]> err.no Git - sope/blob - sope-appserver/SoOFS/OFSBaseObject.m
added strict OSX bundle dependencies
[sope] / sope-appserver / SoOFS / OFSBaseObject.m
1 /*
2   Copyright (C) 2002-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 "OFSBaseObject.h"
23 #include "OFSFactoryContext.h"
24 #include "OFSFolder.h"
25 #include "common.h"
26
27 @implementation OFSBaseObject
28
29 + (int)version {
30   return 1;
31 }
32
33 - (void)dealloc {
34   [self detachFromContainer];
35   [self->name        release];
36   [self->fileManager release];
37   [self->storagePath release];
38   [self->soClass     release];
39   [super dealloc];
40 }
41
42 /* awake */
43
44 - (NSException *)takeStorageInfoFromContext:(OFSFactoryContext *)_ctx {
45   self->fileManager = [[_ctx fileManager] retain];
46   self->storagePath = [[_ctx storagePath] copy];
47   [self setContainer:[_ctx container] andName:[_ctx nameInContainer]];
48   return nil;
49 }
50
51 - (id)awakeFromFetchInContext:(OFSFactoryContext *)_ctx {
52   if (self->fileManager == nil || self->storagePath == nil)
53     [self logWithFormat:@"WARNING: object has no storage info !"];
54   
55   return self;
56 }
57 - (id)awakeFromInsertionInContext:(OFSFactoryContext *)_ctx {
58   self->fileManager = [[_ctx fileManager] retain];
59   self->storagePath = [[_ctx storagePath] copy];
60   [self setContainer:[_ctx container] andName:[_ctx nameInContainer]];
61   return self;
62 }
63
64 /* accessors */
65
66 - (SoClass *)soClass {
67   if (self->soClass == nil)
68     return [super soClass];
69   return self->soClass;
70 }
71
72 - (id<NSObject,NGFileManager>)fileManager {
73   return self->fileManager;
74 }
75 - (NSString *)storagePath {
76   return self->storagePath;
77 }
78 - (EOGlobalID *)globalID {
79   return [[self fileManager] globalIDForPath:[self storagePath]];
80 }
81
82 - (BOOL)isCollection {
83   return NO;
84 }
85 - (BOOL)hasChildren {
86   return [self isCollection];
87 }
88 - (BOOL)doesExist {
89   return [[self fileManager] fileExistsAtPath:[self storagePath]];
90 }
91
92 /* containment */
93
94 - (id)container {
95   return self->container;
96 }
97 - (NSString *)nameInContainer {
98   return self->name;
99 }
100 - (void)setContainer:(id)_container andName:(NSString *)_name {
101   self->container = _container;
102   ASSIGNCOPY(self->name, _name);
103 }
104
105 /* operations */
106
107 - (void)detachFromContainer {
108   self->container = nil;
109   [self->name release]; self->name = nil;
110 }
111 - (BOOL)isAttachedToContainer {
112   return self->container ? YES : NO;
113 }
114
115 - (id)DELETEAction:(id)_ctx {
116   NSException *e;
117   id fm;
118   
119   if ((e = [self validateForDelete]))
120     return e;
121   
122   if ((fm = [self fileManager]) == nil) {
123     [self logWithFormat:@"missing filemanager for delete."];
124     return [NSException exceptionWithHTTPStatus:500 /* server error */
125                         reason:@"missing filemanager for object ?!"];
126   }
127   
128   if (![self doesExist])
129     return [NSException exceptionWithHTTPStatus:404 /* not found */];
130   
131   if ([fm removeFileAtPath:[self storagePath] handler:nil])
132     /* nil means "everything OK" ;-) [for the WebDAV renderer] */
133     return [NSNumber numberWithBool:YES];
134   
135   if ([fm respondsToSelector:@selector(lastException)])
136     return [fm lastException];
137   
138   return [NSException exceptionWithHTTPStatus:500 /* server error */
139                       reason:@"filemanager couldn't remove file at path."];
140 }
141
142 /* KVC */
143
144 - (id)handleQueryWithUnboundKey:(NSString *)key {
145   // TODO: any drawbacks when doing this ?
146   return nil;
147 }
148
149 - (id)valueForKey:(NSString *)_name {
150   /* map out some very private keys */
151   unsigned nl;
152   unichar  c;
153   
154   if ((nl = [_name length]) == 0)
155     return nil;
156   
157   c = [_name characterAtIndex:0];
158   if ((c == 's') && (nl == 11)) {
159     if ([_name isEqualToString:@"storagePath"])
160       /* do not allow KVC access to storage path */
161       return nil;
162   }
163   else if ((c == 'f') && (nl == 11)) {
164     if ([_name isEqualToString:@"fileManager"])
165       /* do not allow KVC access to filemanager */
166       return nil;
167   }
168   
169   return [super valueForKey:_name];
170 }
171
172 /* key validations */
173
174 - (NSException *)validateForDelete {
175   return nil;
176 }
177 - (NSException *)validateForInsert {
178   return nil;
179 }
180 - (NSException *)validateForUpdate {
181   return nil;
182 }
183 - (NSException *)validateForSave {
184   return nil;
185 }
186
187 /* WebDAV */
188
189 - (NSString *)davDisplayName {
190   NSString *s;
191   if ((s = [self valueForKey:@"NSFileSubject"])) return s;
192   return [self nameInContainer];
193 }
194 - (id)davLastModified {
195   return [self valueForKey:NSFileModificationDate];
196 }
197
198 /* schema */
199
200 - (NSClassDescription *)soClassDescription {
201   return nil;
202 }
203
204 /* security */
205
206 - (NSString *)ownerInContext:(id)_ctx {
207   /* ask container ... */
208   id c;
209   
210   if ((c = [self container]) == nil)
211     return nil;
212
213   if ([c respondsToSelector:@selector(ownerOfChild:inContext:)])
214     return [c ownerOfChild:self inContext:_ctx];
215
216   if (c == self)
217     /* avoid endless recursion ... */
218     return nil;
219
220   return [c ownerInContext:_ctx];
221 }
222
223 - (id)authenticatorInContext:(id)_ctx {
224   /* ask container ... */
225   id lContainer;
226   
227   if ((lContainer = [self container]) == nil)
228     return nil;
229
230   if (lContainer == self)
231     /* avoid endless recursion ... */
232     return nil;
233
234   return [lContainer authenticatorInContext:_ctx];
235 }
236
237 /* version control */
238
239 - (BOOL)isCvsControlled {
240   return NO;
241 }
242 - (BOOL)isSvnControlled {
243   return NO;
244 }
245
246 /* debugging */
247
248 - (BOOL)isDebuggingEnabled {
249 #if DEBUG
250   return YES;
251 #else
252   return NO;
253 #endif
254 }
255 - (NSString *)loggingPrefix {
256   /* improve perf ... */
257   NSString *n = [self nameInContainer];
258   return [NSString stringWithFormat:@"0x%08X[%@]:%@",
259                      self, NSStringFromClass([self class]),
260                      n ? n : @"ROOT"];
261 }
262
263 /* description */
264
265 - (NSString *)description {
266   NSMutableString *ms;
267
268   ms = [NSMutableString stringWithCapacity:64];
269   [ms appendFormat:@"<0x%08X[%@]:", self, NSStringFromClass([self class])];
270   
271   if (self->storagePath) 
272     [ms appendFormat:@" path=%@", self->storagePath];
273   
274   [ms appendString:@">"];
275   return ms;
276 }
277
278 @end /* OFSBaseObject */