00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <microfeed-common/microfeedconfiguration.h>
00021 #include <microfeed-common/microfeedmisc.h>
00022 #include <microfeed-common/microfeedstore.h>
00023
00024 #include <stdlib.h>
00025 #include <string.h>
00026 #include <sys/types.h>
00027 #include <sys/stat.h>
00028 #include <fcntl.h>
00029 #include <unistd.h>
00030 #include <libgen.h>
00031
00032 struct _MicrofeedConfiguration {
00033 char* providers_environment_directory;
00034 char* providers_home_directory;
00035 char* publishers_environment_directory;
00036 char* publishers_home_directory;
00037 char* subscribers_environment_directory;
00038 char* subscribers_home_directory;
00039 char* wizards_environment_directory;
00040 char* wizards_home_directory;
00041 const char** providers;
00042 const char** provider_directories;
00043 const char** provider_names;
00044 const char*** provider_feeds;
00045 const char** publishers;
00046 const char** publisher_directories;
00047 MicrofeedStore* subscriptions;
00048 const char** wizards;
00049 const char** wizard_directories;
00050 const char** wizard_names;
00051 const char*** wizard_settings;
00052 };
00053
00054 typedef struct {
00055 char* application_identifier;
00056 char* filename;
00057 const char** subscriptions;
00058 } Subscription;
00059
00060 static Subscription* subscription_new(const char* application_identifier, const char* filename, const char** subscriptions);
00061 static void subscription_free(Subscription* subscription);
00062 static const char* subscription_get_application_identifier(Subscription* subscription);
00063 static void subscription_save(Subscription* subscription);
00064
00065 static ssize_t read_line(int fd, size_t offset, char* buffer, size_t buffer_size);
00066 static void get_providers(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer);
00067 static void get_publishers(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer);
00068 static void get_wizards(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer);
00069 static void update_providers(MicrofeedConfiguration* configuration);
00070 static void update_publishers(MicrofeedConfiguration* configuration);
00071 static void update_wizards(MicrofeedConfiguration* configuration);
00072 static int update_and_get_provider_index(MicrofeedConfiguration* configuration, const char* provider_identifier);
00073 static int update_and_get_wizard_index(MicrofeedConfiguration* configuration, const char* provider_identifier);
00074 static Subscription* update_and_get_subscription(MicrofeedConfiguration* configuration, const char* application_identifier);
00075
00076 MicrofeedConfiguration* microfeed_configuration_new(void) {
00077 MicrofeedConfiguration* configuration;
00078 char* directory;
00079 size_t length;
00080
00081 configuration = microfeed_memory_allocate(MicrofeedConfiguration);
00082 if ((directory = getenv("MICROFEED_PROVIDERS_DIRECTORY"))) {
00083 configuration->providers_environment_directory = strdup(directory);
00084 }
00085 if ((directory = getenv("MICROFEED_PUBLISHERS_DIRECTORY"))) {
00086 configuration->publishers_environment_directory = strdup(directory);
00087 }
00088 if ((directory = getenv("MICROFEED_SUBSCRIBERS_DIRECTORY"))) {
00089 configuration->subscribers_environment_directory = strdup(directory);
00090 }
00091 if ((directory = getenv("MICROFEED_WIZARDS_DIRECTORY"))) {
00092 configuration->wizards_environment_directory = strdup(directory);
00093 }
00094 if ((directory = getenv("HOME"))) {
00095 length = strlen(directory);
00096 configuration->providers_home_directory = microfeed_memory_allocate_bytes(length + 22);
00097 memcpy(configuration->providers_home_directory, directory, length);
00098 memcpy(configuration->providers_home_directory + length, "/.microfeed/providers", 22);
00099 configuration->publishers_home_directory = microfeed_memory_allocate_bytes(length + 23);
00100 memcpy(configuration->publishers_home_directory, directory, length);
00101 memcpy(configuration->publishers_home_directory + length, "/.microfeed/publishers", 23);
00102 configuration->subscribers_home_directory = microfeed_memory_allocate_bytes(length + 24);
00103 memcpy(configuration->subscribers_home_directory, directory, length);
00104 memcpy(configuration->subscribers_home_directory + length, "/.microfeed/subscribers", 24);
00105 configuration->wizards_home_directory = microfeed_memory_allocate_bytes(length + 20);
00106 memcpy(configuration->wizards_home_directory, directory, length);
00107 memcpy(configuration->wizards_home_directory + length, "/.microfeed/wizards", 20);
00108 }
00109 configuration->subscriptions = microfeed_store_new_sorted((MicrofeedStoreCompareKeysFunction)strcmp, (MicrofeedStoreGetKeyFunction)subscription_get_application_identifier);
00110
00111 return configuration;
00112 }
00113
00114 void microfeed_configuration_free(MicrofeedConfiguration* configuration) {
00115 microfeed_configuration_invalidate(configuration);
00116 free(configuration->providers_environment_directory);
00117 free(configuration->publishers_environment_directory);
00118 free(configuration->subscribers_environment_directory);
00119 free(configuration->wizards_environment_directory);
00120 microfeed_memory_free(configuration->providers_home_directory);
00121 microfeed_memory_free(configuration->publishers_home_directory);
00122 microfeed_memory_free(configuration->subscribers_home_directory);
00123 microfeed_store_free(configuration->subscriptions);
00124 microfeed_memory_free(configuration->wizards_home_directory);
00125
00126 microfeed_memory_free(configuration);
00127 }
00128
00129 void microfeed_configuration_invalidate(MicrofeedConfiguration* configuration) {
00130 int i;
00131 int k;
00132
00133 if (configuration->providers) {
00134 for (i = 0; configuration->providers[i]; i++) {
00135 free((void*)configuration->providers[i]);
00136
00137 free((void*)configuration->provider_names[i]);
00138 if (configuration->provider_feeds[i]) {
00139 for (k = 0; configuration->provider_feeds[i][k]; k++) {
00140 free((void*)configuration->provider_feeds[i][k]);
00141 }
00142 free(configuration->provider_feeds[i]);
00143 }
00144 }
00145 free(configuration->providers);
00146 free(configuration->provider_names);
00147 free(configuration->provider_feeds);
00148 free(configuration->provider_directories);
00149 configuration->providers = NULL;
00150 configuration->provider_names = NULL;
00151 configuration->provider_feeds = NULL;
00152 configuration->provider_directories = NULL;
00153 }
00154
00155 if (configuration->publishers) {
00156 for (i = 0; configuration->publishers[i]; i++) {
00157 free((void*)configuration->publishers[i]);
00158
00159 }
00160 free(configuration->publishers);
00161 free(configuration->publisher_directories);
00162 configuration->publishers = NULL;
00163 configuration->publisher_directories = NULL;
00164 }
00165 microfeed_store_remove_and_free_all(configuration->subscriptions, (MicrofeedStoreFreeDataFunction)subscription_free);
00166 if (configuration->wizards) {
00167 for (i = 0; configuration->wizards[i]; i++) {
00168 free((void*)configuration->wizards[i]);
00169
00170 free((void*)configuration->wizard_names[i]);
00171 if (configuration->wizard_settings[i]) {
00172 for (k = 0; configuration->wizard_settings[i][k]; k++) {
00173 free((void*)configuration->wizard_settings[i][k]);
00174 }
00175 free(configuration->wizard_settings[i]);
00176 }
00177 }
00178 free(configuration->wizards);
00179 free(configuration->wizard_names);
00180 free(configuration->wizard_settings);
00181 free(configuration->wizard_directories);
00182 configuration->wizards = NULL;
00183 configuration->wizard_names = NULL;
00184 configuration->wizard_settings = NULL;
00185 configuration->wizard_directories = NULL;
00186 }
00187 }
00188
00189 const char** microfeed_configuration_get_providers(MicrofeedConfiguration* configuration) {
00190 if (!configuration->providers) {
00191 update_providers(configuration);
00192 }
00193
00194 return configuration->providers;
00195 }
00196
00197 const char* microfeed_configuration_get_provider_name(MicrofeedConfiguration* configuration, const char* provider_identifier) {
00198 const char* name = NULL;
00199 int index;
00200
00201 if ((index = update_and_get_provider_index(configuration, provider_identifier)) != -1) {
00202 name = configuration->provider_names[index];
00203 }
00204
00205 return name;
00206 }
00207
00208 const char* microfeed_configuration_get_provider_directory(MicrofeedConfiguration* configuration, const char* provider_identifier) {
00209 const char* directory = NULL;
00210 unsigned int index;
00211 int difference = 1;
00212
00213 if (!configuration->providers) {
00214 update_providers(configuration);
00215 }
00216 if (configuration->providers) {
00217 for (index = 0; configuration->providers[index] && (difference = strcmp(configuration->providers[index], provider_identifier)) < 0; index++) {
00218 }
00219 if (!difference) {
00220 directory = configuration->provider_directories[index];
00221 }
00222 }
00223
00224 return directory;
00225 }
00226
00227 const char** microfeed_configuration_get_publishers(MicrofeedConfiguration* configuration) {
00228 if (!configuration->publishers) {
00229 update_publishers(configuration);
00230 }
00231
00232 return configuration->publishers;
00233 }
00234
00235 const char* microfeed_configuration_get_publisher_directory(MicrofeedConfiguration* configuration, const char* publisher_identifier) {
00236 const char* directory = NULL;
00237 unsigned int index;
00238 int difference = 1;
00239
00240 if (!configuration->publishers) {
00241 update_publishers(configuration);
00242 }
00243 if (configuration->publishers) {
00244 for (index = 0, difference = 1; configuration->publishers[index] && (difference = strcmp(configuration->publishers[index], publisher_identifier)) < 0; index++) {
00245 }
00246 if (!difference) {
00247 directory = configuration->publisher_directories[index];
00248 }
00249 }
00250
00251 return directory;
00252 }
00253
00254 const char* microfeed_configuration_get_default_publisher_directory(MicrofeedConfiguration* configuration) {
00255
00256 return (configuration->publishers_environment_directory ? configuration->publishers_environment_directory : configuration->publishers_home_directory);
00257 }
00258
00259 const char** microfeed_configuration_get_providers_predefined_feed_uris(MicrofeedConfiguration* configuration, const char* provider_identifier) {
00260 const char** feeds = NULL;
00261 int index;
00262
00263 if ((index = update_and_get_provider_index(configuration, provider_identifier)) != -1) {
00264 feeds = configuration->provider_feeds[index];
00265 }
00266
00267 return feeds;
00268 }
00269
00270 const char** microfeed_configuration_get_subscriptions(MicrofeedConfiguration* configuration, const char* application_identifier) {
00271 Subscription* subscription;
00272
00273 if (!(subscription = microfeed_store_get(configuration->subscriptions, application_identifier, Subscription))) {
00274 subscription = update_and_get_subscription(configuration, application_identifier);
00275 }
00276
00277 return (subscription ? subscription->subscriptions : NULL);
00278 }
00279
00280 void microfeed_configuration_add_subscription(MicrofeedConfiguration* configuration, const char* application_identifier, const char* publisher_identifier) {
00281 Subscription* subscription;
00282 int found;
00283 int i;
00284
00285 if (!(subscription = microfeed_store_get(configuration->subscriptions, application_identifier, Subscription))) {
00286 subscription = update_and_get_subscription(configuration, application_identifier);
00287 }
00288 if (subscription) {
00289 found = 0;
00290 for (i = 0; subscription->subscriptions[i]; i++) {
00291 if (!strcmp(subscription->subscriptions[i], publisher_identifier)) {
00292 found = 1;
00293 }
00294 }
00295 if (!found) {
00296 subscription->subscriptions = (const char**)realloc(subscription->subscriptions, (i + 2) * sizeof(char*));
00297 subscription->subscriptions[i] = strdup(publisher_identifier);
00298 subscription->subscriptions[i + 1] = NULL;
00299
00300 subscription_save(subscription);
00301 }
00302 }
00303 }
00304
00305 void microfeed_configuration_remove_subscription(MicrofeedConfiguration* configuration, const char* application_identifier, const char* publisher_identifier) {
00306 Subscription* subscription;
00307 int i;
00308 int index;
00309
00310 if (!(subscription = microfeed_store_get(configuration->subscriptions, application_identifier, Subscription))) {
00311 subscription = update_and_get_subscription(configuration, application_identifier);
00312 }
00313 if (subscription) {
00314 index = -1;
00315 for (i = 0; subscription->subscriptions[i]; i++) {
00316 if (!strcmp(subscription->subscriptions[i], publisher_identifier)) {
00317 index = i;
00318 }
00319 }
00320 if (index != -1) {
00321 subscription->subscriptions = (const char**)realloc(subscription->subscriptions, i * sizeof(char*));
00322 memmove(subscription->subscriptions + index, subscription->subscriptions + index + 1, (i - index) * sizeof(const char**));
00323
00324 subscription_save(subscription);
00325 }
00326 }
00327 }
00328
00329 int microfeed_configuration_is_subscribed(MicrofeedConfiguration* configuration, const char* application_identifier, const char* publisher_identifier) {
00330 int found = 0;
00331 Subscription* subscription;
00332 int i;
00333
00334 if (!(subscription = microfeed_store_get(configuration->subscriptions, application_identifier, Subscription))) {
00335 subscription = update_and_get_subscription(configuration, application_identifier);
00336 }
00337 if (subscription) {
00338 found = 0;
00339 for (i = 0; subscription->subscriptions[i]; i++) {
00340 if (!strcmp(subscription->subscriptions[i], publisher_identifier)) {
00341 found = 1;
00342 break;
00343 }
00344 }
00345 }
00346
00347 return found;
00348 }
00349
00350 const char** microfeed_configuration_get_wizards(MicrofeedConfiguration* configuration) {
00351 if (!configuration->wizards) {
00352 update_wizards(configuration);
00353 }
00354
00355 return configuration->wizards;
00356 }
00357
00358 const char* microfeed_configuration_get_wizard_name(MicrofeedConfiguration* configuration, const char* publisher_identifier) {
00359 const char* name = NULL;
00360 int index;
00361
00362 if ((index = update_and_get_wizard_index(configuration, publisher_identifier)) != -1) {
00363 name = configuration->wizard_names[index];
00364 }
00365
00366 return name;
00367 }
00368
00369 const char** microfeed_configuration_get_wizard_settings(MicrofeedConfiguration* configuration, const char* publisher_identifier) {
00370 const char** settings = NULL;
00371 int index;
00372
00373 if ((index = update_and_get_wizard_index(configuration, publisher_identifier)) != -1) {
00374 settings = configuration->wizard_settings[index];
00375 }
00376
00377 return settings;
00378
00379 }
00380
00381 static Subscription* subscription_new(const char* application_identifier, const char* filename, const char** subscription_strings) {
00382 Subscription* subscription;
00383
00384 subscription = microfeed_memory_allocate(Subscription);
00385 subscription->application_identifier = strdup(application_identifier);
00386 subscription->filename = strdup(filename);
00387 subscription->subscriptions = subscription_strings;
00388
00389 return subscription;
00390 }
00391
00392 static void subscription_free(Subscription* subscription) {
00393 int i;
00394
00395 free(subscription->application_identifier);
00396 free(subscription->filename);
00397 for (i = 0; subscription->subscriptions[i]; i++) {
00398 free((void*)subscription->subscriptions[i]);
00399 }
00400 free(subscription->subscriptions);
00401 }
00402
00403 static const char* subscription_get_application_identifier(Subscription* subscription) {
00404
00405 return subscription->application_identifier;
00406 }
00407
00408 static void subscription_save(Subscription* subscription) {
00409 char* file;
00410 char* directory;
00411 int fd;
00412 int i;
00413
00414 file = strdup(subscription->filename);
00415 directory = dirname(file);
00416 microfeed_util_create_directory_recursively(directory);
00417 free(file);
00418
00419 if ((fd = open(subscription->filename, O_WRONLY | O_CREAT | O_TRUNC, 0666)) != -1) {
00420 for (i = 0; subscription->subscriptions[i]; i++) {
00421 write(fd, subscription->subscriptions[i], strlen(subscription->subscriptions[i]));
00422 write(fd, "\n", 1);
00423 }
00424 close(fd);
00425 }
00426 }
00427
00428 static ssize_t read_line(int fd, size_t offset, char* buffer, size_t buffer_size) {
00429 ssize_t length = -1;
00430 size_t i;
00431
00432 if (lseek(fd, offset, SEEK_SET) != -1) {
00433 if ((length = read(fd, buffer, buffer_size)) > 0) {
00434 for (i = 0; i < length && buffer[i] != '\n' && buffer[i] != '\r'; i++) {
00435 }
00436 if (i == buffer_size) {
00437 length = 0;
00438 } else {
00439 buffer[i] = 0;
00440 length = i + 1;
00441 }
00442 }
00443 }
00444
00445 return length;
00446 }
00447
00448 static void get_providers(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer) {
00449 DIR* dir;
00450 struct dirent* dirent;
00451 int i;
00452 int order;
00453
00454 if ((dir = opendir(directory))) {
00455 while ((dirent = readdir(dir))) {
00456 if (dirent->d_name[0] != '.') {
00457 for (i = 0; i < *length_pointer; i++) {
00458 if ((order = strcmp(configuration->providers[i], dirent->d_name)) >= 0) {
00459 break;
00460 }
00461 }
00462 if (i == *length_pointer || order != 0) {
00463 (*length_pointer)++;
00464 configuration->providers = (const char**)realloc(configuration->providers, (*length_pointer + 1) * sizeof(char*));
00465 configuration->provider_directories = (const char**)realloc(configuration->provider_directories, *length_pointer * sizeof(char*));
00466 configuration->provider_names = (const char**)realloc(configuration->provider_names, *length_pointer * sizeof(char*));
00467 configuration->provider_feeds = (const char***)realloc(configuration->provider_feeds, *length_pointer * sizeof(char**));
00468 if (i < *length_pointer - 1) {
00469 memmove(configuration->providers + i + 1, configuration->providers + i, (*length_pointer - i - 1) * sizeof(char*));
00470 memmove(configuration->provider_directories + i + 1, configuration->provider_directories + i, (*length_pointer - i - 1) * sizeof(char*));
00471 memmove(configuration->provider_names + i + 1, configuration->provider_names + i, (*length_pointer - i - 1) * sizeof(char*));
00472 memmove(configuration->provider_feeds + i + 1, configuration->provider_feeds + i, (*length_pointer - i - 1) * sizeof(char*));
00473 }
00474 configuration->providers[i] = strdup(dirent->d_name);
00475 configuration->provider_directories[i] = directory;
00476 configuration->provider_names[i] = NULL;
00477 configuration->provider_feeds[i] = NULL;
00478 configuration->providers[*length_pointer] = NULL;
00479 }
00480 }
00481 }
00482 closedir(dir);
00483 }
00484 }
00485
00486 static void get_publishers(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer) {
00487 DIR* dir;
00488 struct dirent* dirent;
00489 int i;
00490 int order;
00491
00492 if ((dir = opendir(directory))) {
00493 while ((dirent = readdir(dir))) {
00494 if (dirent->d_name[0] != '.') {
00495 for (i = 0; i < *length_pointer; i++) {
00496 if ((order = strcmp(configuration->publishers[i], dirent->d_name)) >= 0) {
00497 break;
00498 }
00499 }
00500 if (i == *length_pointer || order != 0) {
00501 (*length_pointer)++;
00502 configuration->publishers = (const char**)realloc(configuration->publishers, (*length_pointer + 1) * sizeof(char*));
00503 configuration->publisher_directories = (const char**)realloc(configuration->publisher_directories, *length_pointer * sizeof(char*));
00504 if (i < *length_pointer - 1) {
00505 memmove(configuration->publishers + i + 1, configuration->publishers + i, (*length_pointer - i - 1) * sizeof(char*));
00506 memmove(configuration->publisher_directories + i + 1, configuration->publisher_directories + i, (*length_pointer - i - 1) * sizeof(char*));
00507 }
00508 configuration->publishers[i] = strdup(dirent->d_name);
00509 configuration->publisher_directories[i] = directory;
00510 configuration->publishers[*length_pointer] = NULL;
00511 }
00512 }
00513 }
00514 closedir(dir);
00515 }
00516 }
00517
00518 static void get_wizards(MicrofeedConfiguration* configuration, const char* directory, unsigned int* length_pointer) {
00519 DIR* dir;
00520 struct dirent* dirent;
00521 int i;
00522 int order;
00523
00524 if ((dir = opendir(directory))) {
00525 while ((dirent = readdir(dir))) {
00526 if (dirent->d_name[0] != '.') {
00527 for (i = 0; i < *length_pointer; i++) {
00528 if ((order = strcmp(configuration->wizards[i], dirent->d_name)) >= 0) {
00529 break;
00530 }
00531 }
00532 if (i == *length_pointer || order != 0) {
00533 (*length_pointer)++;
00534 configuration->wizards = (const char**)realloc(configuration->wizards, (*length_pointer + 1) * sizeof(char*));
00535 configuration->wizard_directories = (const char**)realloc(configuration->wizard_directories, *length_pointer * sizeof(char*));
00536 configuration->wizard_names = (const char**)realloc(configuration->wizard_names, *length_pointer * sizeof(char*));
00537 configuration->wizard_settings = (const char***)realloc(configuration->wizard_settings, *length_pointer * sizeof(char**));
00538 if (i < *length_pointer - 1) {
00539 memmove(configuration->wizards + i + 1, configuration->wizards + i, (*length_pointer - i - 1) * sizeof(char*));
00540 memmove(configuration->wizard_directories + i + 1, configuration->wizard_directories + i, (*length_pointer - i - 1) * sizeof(char*));
00541 memmove(configuration->wizard_names + i + 1, configuration->wizard_names + i, (*length_pointer - i - 1) * sizeof(char*));
00542 memmove(configuration->wizard_settings + i + 1, configuration->wizard_settings + i, (*length_pointer - i - 1) * sizeof(char*));
00543 }
00544 configuration->wizards[i] = strdup(dirent->d_name);
00545 configuration->wizard_directories[i] = directory;
00546 configuration->wizard_names[i] = NULL;
00547 configuration->wizard_settings[i] = NULL;
00548 configuration->wizards[*length_pointer] = NULL;
00549 }
00550 }
00551 }
00552 closedir(dir);
00553 }
00554 }
00555
00556 static Subscription* get_subscription(MicrofeedConfiguration* configuration, const char* application_identifier, const char* directory) {
00557 Subscription* subscription = NULL;
00558 const char** strings = NULL;
00559 char* filename;
00560 int fd;
00561 char buffer[1024];
00562 size_t offset;
00563 ssize_t length;
00564 int i;
00565
00566 strings = (const char**)malloc(sizeof(char*));
00567 strings[0] = NULL;
00568 filename = microfeed_util_string_concatenate(directory, "/", application_identifier, NULL);
00569 if ((fd = open(filename, O_RDONLY)) != -1) {
00570 offset = 0;
00571 for (i = 0; (length = read_line(fd, offset, buffer, 1024)) > 0; i++) {
00572 strings = (const char**)realloc(strings, (i + 2) * sizeof(char*));
00573 strings[i] = strdup(buffer);
00574 offset += length;
00575 }
00576 strings[i] = NULL;
00577 close(fd);
00578 }
00579 subscription = subscription_new(application_identifier, filename, strings);
00580 free(filename);
00581
00582 return subscription;
00583 }
00584
00585 static void update_providers(MicrofeedConfiguration* configuration) {
00586 unsigned int length;
00587
00588 length = 0;
00589 if (configuration->providers_environment_directory) {
00590 get_providers(configuration, configuration->providers_environment_directory, &length);
00591 }
00592 if (configuration->providers_home_directory) {
00593 get_providers(configuration, configuration->providers_home_directory, &length);
00594 }
00595 get_providers(configuration, "/usr/local/lib/microfeed/providers", &length);
00596 get_providers(configuration, "/usr/lib/microfeed/providers", &length);
00597 }
00598
00599 static void update_publishers(MicrofeedConfiguration* configuration) {
00600 unsigned int length;
00601
00602 length = 0;
00603 if (configuration->publishers_environment_directory) {
00604 get_publishers(configuration, configuration->publishers_environment_directory, &length);
00605 }
00606 if (configuration->publishers_home_directory) {
00607 get_publishers(configuration, configuration->publishers_home_directory, &length);
00608 }
00609 get_publishers(configuration, "/usr/local/lib/microfeed/publishers", &length);
00610 get_publishers(configuration, "/usr/lib/microfeed/publishers", &length);
00611 }
00612
00613 static int update_and_get_provider_index(MicrofeedConfiguration* configuration, const char* provider_identifier) {
00614 int index = -1;
00615 char* filename;
00616 int difference = -1;
00617 int fd;
00618 char buffer[1024];
00619 size_t offset;
00620 ssize_t length;
00621 int i;
00622
00623 if (!configuration->providers) {
00624 update_providers(configuration);
00625 }
00626 if (configuration->providers) {
00627 for (index = 0; configuration->providers[index] && (difference = strcmp(configuration->providers[index], provider_identifier)) < 0; index++) {
00628 }
00629 if (!difference) {
00630 if (!configuration->provider_names[index]) {
00631 filename = microfeed_util_string_concatenate(configuration->provider_directories[index], "/", provider_identifier, NULL);
00632 if ((fd = open(filename, O_RDONLY)) != -1) {
00633 offset = 0;
00634 if ((length = read_line(fd, offset, buffer, 1024)) > 0) {
00635 configuration->provider_names[index] = strdup(buffer);
00636 }
00637 offset += length;
00638 for (i = 0; (length = read_line(fd, offset, buffer, 1024)) > 0; i++) {
00639 configuration->provider_feeds[index] = (const char**)realloc(configuration->provider_feeds[index], (i + 2) * sizeof(char*));
00640 configuration->provider_feeds[index][i] = strdup(buffer);
00641 offset += length;
00642 }
00643 configuration->provider_feeds[index][i] = NULL;
00644 close(fd);
00645 }
00646 free(filename);
00647 }
00648 } else {
00649 index = -1;
00650 }
00651 }
00652
00653 return index;
00654 }
00655
00656 static int update_and_get_wizard_index(MicrofeedConfiguration* configuration, const char* provider_identifier) {
00657 int index = -1;
00658 char* filename;
00659 int difference = -1;
00660 int fd;
00661 char buffer[1024];
00662 size_t offset;
00663 ssize_t length;
00664 int i;
00665
00666 if (!configuration->wizards) {
00667 update_wizards(configuration);
00668 }
00669 if (configuration->wizards) {
00670 for (index = 0; configuration->wizards[index] && (difference = strcmp(configuration->wizards[index], provider_identifier)) < 0; index++) {
00671 }
00672 if (!difference) {
00673 if (!configuration->wizard_names[index]) {
00674 filename = microfeed_util_string_concatenate(configuration->wizard_directories[index], "/", provider_identifier, NULL);
00675 if ((fd = open(filename, O_RDONLY)) != -1) {
00676 offset = 0;
00677 if ((length = read_line(fd, offset, buffer, 1024)) > 0) {
00678 configuration->wizard_names[index] = strdup(buffer);
00679 }
00680 offset += length;
00681 for (i = 0; (length = read_line(fd, offset, buffer, 1024)) > 0; i++) {
00682 configuration->wizard_settings[index] = (const char**)realloc(configuration->wizard_settings[index], (i + 2) * sizeof(char*));
00683 configuration->wizard_settings[index][i] = strdup(buffer);
00684 offset += length;
00685 }
00686 configuration->wizard_settings[index][i] = NULL;
00687 close(fd);
00688 }
00689 free(filename);
00690 }
00691 } else {
00692 index = -1;
00693 }
00694 }
00695
00696 return index;
00697 }
00698
00699 static Subscription* update_and_get_subscription(MicrofeedConfiguration* configuration, const char* application_identifier) {
00700 Subscription* subscription = NULL;
00701
00702 if (configuration->subscribers_environment_directory) {
00703 subscription = get_subscription(configuration, application_identifier, configuration->subscribers_environment_directory);
00704 } else if (configuration->subscribers_home_directory) {
00705 subscription = get_subscription(configuration, application_identifier, configuration->subscribers_home_directory);
00706 }
00707
00708 return subscription;
00709 }
00710
00711 static void update_wizards(MicrofeedConfiguration* configuration) {
00712 unsigned int length;
00713
00714 length = 0;
00715 if (configuration->wizards_environment_directory) {
00716 get_wizards(configuration, configuration->wizards_environment_directory, &length);
00717 }
00718 if (configuration->wizards_home_directory) {
00719 get_wizards(configuration, configuration->wizards_home_directory, &length);
00720 }
00721 get_wizards(configuration, "/usr/local/lib/microfeed/wizards", &length);
00722 get_wizards(configuration, "/usr/lib/microfeed/wizards", &length);
00723 }