]> err.no Git - sope/blob - sope-appserver/SoOFS/sope.m
added strict OSX bundle dependencies
[sope] / sope-appserver / SoOFS / sope.m
1 /*
2   Copyright (C) 2000-2005 SKYRIX Software AG
3
4   This file is part of SOPE.
5
6   SOPE is free software; you can redistribute it and/or modify it under
7   the terms of the GNU Lesser General Public License as published by the
8   Free Software Foundation; either version 2, or (at your option) any
9   later version.
10
11   SOPE is distributed in the hope that it will be useful, but WITHOUT ANY
12   WARRANTY; without even the implied warranty of MERCHANTABILITY or
13   FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
14   License for more details.
15
16   You should have received a copy of the GNU Lesser General Public
17   License along with SOPE; see the file COPYING.  If not, write to the
18   Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA
19   02111-1307, USA.
20 */
21
22 #include <SoObjects/SoApplication.h>
23
24 /*
25   An executable which can run a SoOFS based SOPE application. When started,
26   it takes the current-directory path for constructing the SoOFS root folder
27   of the SOPE application.
28   It also reads a file ".sope.plist" in the root-path to load site-local
29   configuration settings.
30   
31   TODO:
32   - load defaults from root-folder
33     DONE [".sope.plist" is loaded and registered]
34   - load products from root-folder
35   - load authenticator from root-folder
36 */
37
38 @class NSString, NSFileManager;
39
40 @interface SOPE : SoApplication
41 {
42   NSFileManager *fm;
43   NSString *rootPath;
44 }
45
46 @end
47
48 #include <SoObjects/SoClassSecurityInfo.h>
49 #include "OFSFolder.h"
50 #include "OFSFactoryContext.h"
51 #include "common.h"
52
53 NSString *SoRootFolder = @"SoRootFolder";
54
55 @implementation SOPE
56
57 static BOOL debugRootObject = NO;
58
59 + (void)initialize {
60   /* 
61      Since we are a tool, we have no bundle and need to declare security info
62      manually ...
63   */
64   SoClassSecurityInfo *si = [self soClassSecurityInfo];
65   [si declareObjectPublic];
66   [si setDefaultAccess:@"allow"];
67 }
68
69 - (void)loadLocalDefaults:(NSString *)_path {
70   NSDictionary *plist;
71
72   if ((plist = [[NSDictionary alloc] initWithContentsOfFile:_path]) == nil) {
73     [self logWithFormat:@"could not read SOPE config: %@", _path];
74     return;
75   }
76   /* 
77      TODO: we need a separate domain for this, this stuff doesn't make sense
78            at all ...
79   */
80   [[NSUserDefaults standardUserDefaults] registerDefaults:plist];
81   [self logWithFormat:@"registered site defaults: %@", _path];
82   [plist release];
83 }
84
85 - (BOOL)_bootstrap {
86   // TODO: create some bootstrap code to create initial user database,
87   //       defaults, control-panel, etc
88   return YES;
89 }
90
91 - (BOOL)_setupRoot {
92   BOOL     isDir;
93   NSString *p;
94
95   /* setup root path */
96   
97   if (self->fm == nil) {
98     [self logWithFormat:@"missing SOPE storage filemanager."];
99     return NO;
100   }
101   if ([self->rootPath length] == 0) {
102     [self logWithFormat:@"missing SOPE storage root-path."];
103     return NO;
104   }
105
106   if (![self->fm fileExistsAtPath:self->rootPath isDirectory:&isDir]) {
107     [self logWithFormat:@"SOPE storage root-path does not exist: %@", 
108             self->rootPath];
109     return NO;
110   }
111   if (!isDir) {
112     [self logWithFormat:@"SOPE storage root-path is not a directory: %@", 
113             self->rootPath];
114     return NO;
115   }
116   
117   /* bootstrap root if necessary */
118   
119   if (![self _bootstrap])
120     return NO;
121   
122   /* configure */
123   
124   [self logWithFormat:@"starting SOPE on OFS root: %@", self->rootPath];
125   
126   p = [self->rootPath stringByAppendingPathComponent:@".sope.plist"];
127   if ([self->fm isReadableFileAtPath:p])
128     [self loadLocalDefaults:p];
129   
130   return YES;
131 }
132
133 - (id)init {
134   if ((self = [super init])) {
135     // TODO: make root-path/fm configurable ?
136     self->fm       = [[NSFileManager defaultManager] retain];
137     self->rootPath = [[self->fm currentDirectoryPath] copy];
138
139     if (![self _setupRoot]) {
140       [self release];
141       return nil;
142     }
143   }
144   return self;
145 }
146 - (void)dealloc {
147   [self->fm       release];
148   [self->rootPath release];
149   [super dealloc];
150 }
151
152 /* accessors */
153
154 - (id)fileManager {
155   return self->fm;
156 }
157 - (NSString *)rootPath {
158   return self->rootPath;
159 }
160
161 /* define the root SoObject */
162
163 - (OFSFolder *)rootObjectInContext:(id)_ctx {
164   OFSFactoryContext *ctx;
165   OFSFolder *root;
166
167   if (debugRootObject) [self logWithFormat:@"queried root object ..."];
168   
169   if ((root = [_ctx valueForKey:SoRootFolder]) != nil) {
170     if (debugRootObject) 
171       [self logWithFormat:@"  using cached root object: %@", root];
172     return root;
173   }
174   
175   ctx = [OFSFactoryContext contextWithFileManager:[self fileManager]
176                            storagePath:[self rootPath]];
177   
178   root = [[[OFSFolder alloc] init] autorelease];
179   [root takeStorageInfoFromContext:ctx];
180   [root awakeFromFetchInContext:ctx];
181   [_ctx takeValue:root forKey:SoRootFolder];
182   if (debugRootObject) 
183     [self logWithFormat:@"  created new root object: %@", root];
184   return root;
185 }
186
187 /* security */
188
189 - (id)authenticatorInContext:(id)_ctx {
190   id root;
191   id auth;
192   
193   root = [self rootObjectInContext:_ctx];
194   if ((auth = [root authenticatorInContext:_ctx]))
195     return auth;
196   
197   return [super authenticatorInContext:_ctx];
198 }
199
200 /* SMI */
201
202 - (NSArray *)manageMenuChildNames {
203   NSMutableArray *ma;
204   id root;
205   
206   ma = [NSMutableArray arrayWithCapacity:16];
207   [ma addObject:@"ControlPanel"];
208   
209   root = [self rootObjectInContext:[self context]];
210   if (root != nil && (root != self)) 
211     [ma addObjectsFromArray:[root toOneRelationshipKeys]];
212   
213   return ma;
214 }
215
216 /* MacOSX support */
217
218 - (id)handleQueryWithUnboundKey:(NSString *)key {
219   /* KVC on MacOSX throws an exception when an unbound key is queried ... */
220   return nil;
221 }
222
223 @end /* SOPE */
224
225 int main(int argc, char **argv, char **env) {
226   NSAutoreleasePool *pool;
227   
228   pool = [[NSAutoreleasePool alloc] init];
229 #if LIB_FOUNDATION_LIBRARY
230   [NSProcessInfo initializeWithArguments:argv count:argc environment:env];
231 #endif
232   
233   WOWatchDogApplicationMain(@"SOPE", argc, (void*)argv);
234   
235   [pool release];
236   return 0;
237 }