Objective c 监视MacOS 10.10上的文件系统事件

Objective c 监视MacOS 10.10上的文件系统事件,objective-c,c,macos,file,xcode6,Objective C,C,Macos,File,Xcode6,我正在尝试使用Xcode(MacOS 10.10下)编写一个小的命令行工具,它监视一个特定的文件夹,并通知我该文件夹中文件的更改。 我正在遵循中给出的指南 这是我目前的代码: #import <Foundation/Foundation.h> #include <CoreServices/CoreServices.h> void mycallback( ConstFSEventStreamRef streamRef,

我正在尝试使用Xcode(MacOS 10.10下)编写一个小的命令行工具,它监视一个特定的文件夹,并通知我该文件夹中文件的更改。 我正在遵循中给出的指南

这是我目前的代码:

#import <Foundation/Foundation.h>
#include <CoreServices/CoreServices.h>



void mycallback(
                ConstFSEventStreamRef streamRef,
                void *clientCallBackInfo,
                size_t numEvents,
                void *eventPaths,
                const FSEventStreamEventFlags eventFlags[],
                const FSEventStreamEventId eventIds[])
{
    int i;
    char **paths = eventPaths;

    printf("Callback called\n");
    for (i=0; i<numEvents; i++) {
        int count;
        /* flags are unsigned long, IDs are uint64_t */
        printf("Change %llu in %s, flags %lu\n", eventIds[i], paths[i], eventFlags[i]);
    }
}


int main(int argc, const char * argv[]) {
    //  @autoreleasepool {
    // insert code here...
    NSLog(@"Starting to watch ");


    /* Define variables and create a CFArray object containing
     CFString objects containing paths to watch.
     */
    CFStringRef mypath = CFSTR("/Users/testuser/");
    CFArrayRef pathsToWatch = CFArrayCreate(NULL, (const void **)&mypath, 1, NULL);
    void *callbackInfo = NULL; // could put stream-specific data here.
    FSEventStreamRef stream;
    CFAbsoluteTime latency = 3.0; /* Latency in seconds */

    /* Create the stream, passing in a callback */
    stream = FSEventStreamCreate(NULL,
                                 &mycallback,
                                 callbackInfo,
                                 pathsToWatch,
                                 kFSEventStreamEventIdSinceNow, /* Or a previous event ID */
                                 latency,
                                 kFSEventStreamCreateFlagNone /* Flags explained in reference */
                                 );



    /* Create the stream before calling this. */
    FSEventStreamScheduleWithRunLoop(stream, CFRunLoopGetCurrent(),kCFRunLoopDefaultMode);

    FSEventStreamStart(stream);

    CFRunLoopRun();

    return 0;
}
#导入
#包括
void mycallback(
ConstFSEventStreamRef streamRef,
void*clientCallBackInfo,
尺寸和数量,
void*事件路径,
常量FSEventStreamEventFlags事件标志[],
常量fseventstreamventid eventIds[]
{
int i;
字符**路径=事件路径;
printf(“调用的回调\n”);

对于(i=0;i您似乎已经注释掉了FSEventStreamRef stream;注释掉了。为了开始观看事件,您需要取消对该行的注释。您的回调打印语句似乎也注释掉了,尽管这可能只是为了调试。

根据文档,在启动事件流发送事件之后,你应该打电话

尝试将
while()
循环更改为:

CFRunLoopRun();
更新。我的输出:

$ ./fsevent
2015-05-17 13:51:29.718 fsevent[898:23601] Starting to watch
Callback called
Change 1165579 in /Users/baf/src/tests/, flags 66560
Callback called
Change 1165594 in /Users/baf/src/tests/, flags 66048

我自己刚刚发现了第一个bug。流必须启动/停止。我编辑了上面的代码示例,但不幸的是它仍然无法工作:-(我在回调函数中取消了printf的注释。//FSEventStreamRef流是一个残余流。该流之前已经声明了几行。我现在删除了该行。但是,代码仍然无法工作:-(感谢提示。我重新设计了该部分代码并启动了RunLoop。但是,没有任何效果:-)我实际上测试了你的代码。它在编译时会给出一系列警告,但它对我来说适用于
CFRunLoopRun()
。查看我的输出现在我完全糊涂了。在我的系统上,唯一的输出是:“2015-05-17 14:01:59.293 testApp[7188:1283738]开始观察“当程序运行时,您是否执行了任何特定的文件操作?”换句话说:程序指示了什么样的更改?另外:您正在运行的是什么平台/操作系统?您在我的输出中看到的是在观察的文件夹中创建和删除文件的结果:
touch test
rm t当然,正如我所写的:“在启动事件流发送事件之后,您应该调用CFRunLoopRun”