From 1373b36739e3da167f8ffb1e471d1988adef268a Mon Sep 17 00:00:00 2001 From: erickson Date: Thu, 15 Sep 2005 22:59:37 +0000 Subject: [PATCH] made C auth server added utils code for C servers, including some fieldmapper handling code fieldmapper now copies headers over to INCLUDE/openils/ install scripts now install c-apps git-svn-id: svn://svn.open-ils.org/ILS/trunk@1832 dcc99617-32d9-48b4-a31d-7c20da2025e4 --- Open-ILS/src/Makefile | 16 +- Open-ILS/src/apachemods/Makefile | 14 +- .../src/apachemods/fieldmapper_lookup-gen.pl | 2 +- Open-ILS/src/c-apps/Makefile | 18 ++ Open-ILS/src/c-apps/oils_auth.c | 214 ++++++++++++++++++ Open-ILS/src/c-apps/oils_utils.c | 25 ++ Open-ILS/src/c-apps/oils_utils.h | 33 +++ OpenSRF/bin/opensrf_all | 2 +- OpenSRF/src/utils/utils.c | 8 +- OpenSRF/src/utils/utils.h | 2 +- install.sh | 2 + 11 files changed, 322 insertions(+), 14 deletions(-) create mode 100644 Open-ILS/src/c-apps/Makefile create mode 100644 Open-ILS/src/c-apps/oils_auth.c create mode 100644 Open-ILS/src/c-apps/oils_utils.c create mode 100644 Open-ILS/src/c-apps/oils_utils.h diff --git a/Open-ILS/src/Makefile b/Open-ILS/src/Makefile index fdaf67d53f..70a0c2cd55 100644 --- a/Open-ILS/src/Makefile +++ b/Open-ILS/src/Makefile @@ -4,12 +4,13 @@ export LDFLAGS = -L $(TMPDIR) -L . export CFLAGS = -g -Wall -O2 -fPIC -I$(LIBXML2_HEADERS) -I$(APACHE2_HEADERS) \ -I$(LIBXML2_HEADERS)/libxml -I$(TMP) -I$(TMPDIR) -export INCLUDEDIR += "/openils/" +export INCDIR = "$(INCLUDEDIR)/openils/" -all: mod_xmltools mod_ils_rest_gateway +all: msg mod_xmltools mod_ils_rest_gateway c_apps -install: perl-install web-install string-templates-install storage-bootstrap cgi-bootstrap xsl-install + +install: perl-install web-install string-templates-install storage-bootstrap cgi-bootstrap xsl-install c_apps-install web-install: webcore-install autojs-install mod_xmltools-install mod_ils_rest_gateway-install @@ -37,9 +38,18 @@ mod_xmltools-install: webcore-install: @echo $@ echo "Copying web into $(WEBDIR)" + # XXX put these back #mkdir -p $(WEBDIR) #cp -r ../web/* $(WEBDIR) +c_apps: mod_ils_rest_gateway + @echo $@ + make -C c-apps + +c_apps-install: + @echo $@ + make -C c-apps install + autojs-install: @echo $@ cp extras/fieldmapper.pl $(BINDIR) diff --git a/Open-ILS/src/apachemods/Makefile b/Open-ILS/src/apachemods/Makefile index 380f6aa3bd..816a885b34 100644 --- a/Open-ILS/src/apachemods/Makefile +++ b/Open-ILS/src/apachemods/Makefile @@ -21,15 +21,18 @@ fieldmapper_lookup.c: # ------------------------------------------------------ mod_xmltools.so: mod_xmltools.o apachetools.o xmltools.o - echo $@ + @echo $@ $(CC) $(LDFLAGS) $(LDLIBS) -shared -W1 apachetools.o xmltools.o mod_xmltools.o -o $@ libfieldmapper.so: fieldmapper_lookup.o - echo $@ + @echo $@ + mkdir -p $(TMPDIR)/openils/ + cp fieldmapper_lookup.h $(TMPDIR)/openils/ $(CC) $(LDFLAGS) $(LDLIBS) -shared -W1 fieldmapper_lookup.o -o $@ + cp libfieldmapper.so $(TMPDIR)/libfieldmapper.so mod_ils_rest_gateway.so: libfieldmapper.so ils_rest_gateway.o json_xml.o - echo $@ + @echo $@ $(CC) $(LDFLAGS) $(LDLIBS) -shared -W1 json_xml.o ils_rest_gateway.o -lfieldmapper -o $@ # ------------------------------------------------------ @@ -37,8 +40,9 @@ mod_ils_rest_gateway.so: libfieldmapper.so ils_rest_gateway.o json_xml.o libfieldmapper-install: libfieldmapper.so echo installing libfieldmapper.so - mkdir -p $(INCLUDEDIR)/ - cp fieldmapper_lookup.h $(INCLUDEDIR)/ + mkdir -p $(INCDIR)/ + @echo "Copying fieldmapper_lookup.h to $(INCDIR)" + cp fieldmapper_lookup.h $(INCDIR)/ cp libfieldmapper.so $(LIBDIR)/libfieldmapper.so diff --git a/Open-ILS/src/apachemods/fieldmapper_lookup-gen.pl b/Open-ILS/src/apachemods/fieldmapper_lookup-gen.pl index f3ae1798c5..76f4c00e24 100755 --- a/Open-ILS/src/apachemods/fieldmapper_lookup-gen.pl +++ b/Open-ILS/src/apachemods/fieldmapper_lookup-gen.pl @@ -68,7 +68,7 @@ print SOURCE <params, 0))) ) { + + seed = va_list_to_string( "%d.%d.%s", time(NULL), getpid(), username ); + key = va_list_to_string( "%s%s", OILS_AUTH_CACHE_PRFX, username ); + + md5seed = md5sum(seed); + osrfCachePutString( key, md5seed, 30 ); + + osrfLog( OSRF_DEBUG, "oilsAuthInit(): has seed %s and key %s", md5seed, key ); + + resp = jsonNewObject(md5seed); + osrfAppRequestRespondComplete( ctx->session, ctx->request, resp ); + + jsonObjectFree(resp); + free(seed); + free(md5seed); + free(key); + return 0; + } + + return -1; +} + + +int oilsAuthComplete( osrfMethodContext* ctx ) { + OSRF_METHOD_VERIFY_CONTEXT(ctx); + + char* uname = jsonObjectGetString(jsonObjectGetIndex(ctx->params, 0)); + char* password = jsonObjectGetString(jsonObjectGetIndex(ctx->params, 1)); + char* storageMethod = "open-ils.storage.direct.actor.user.search.usrname.atomic"; + + if( uname && password ) { + + /* grab the user object from storage */ + osrfLog( OSRF_DEBUG, "oilsAuth calling method %s with username %s", storageMethod, uname ); + + osrfAppSession* session = osrfAppSessionClientInit( "open-ils.storage" ); /**/ + jsonObject* params = jsonNewObject(uname); /**/ + int reqid = osrfAppSessionMakeRequest( session, params, storageMethod, 1, NULL ); + jsonObjectFree(params); + osrfMessage* omsg = osrfAppSessionRequestRecv( session, reqid, 60 ); /**/ + + if(!omsg) { + osrfAppSessionFree(session); + return osrfAppRequestRespondException( ctx->session, ctx->request, + "No response from storage server for method %s", storageMethod ); + } + + jsonObject* userObj = osrfMessageGetResult(omsg); + + char* _j = jsonObjectToJSON(userObj); + osrfLog( OSRF_DEBUG, "Auth received user object from storage: %s", _j ); + free(_j); + + /* the method is atomic, grab the first user we receive */ + if( userObj ) userObj = jsonObjectGetIndex(userObj, 0); + + if(!userObj) { /* XXX needs to be a 'friendly' exception */ + osrfMessageFree(omsg); + osrfAppSessionFree(session); + return osrfAppRequestRespondException( ctx->session, + ctx->request, "User %s not found in the database", uname ); + } + + char* realPassword = oilsFMGetString( userObj, "passwd" ); /**/ + char* seed = osrfCacheGetString( "%s%s", OILS_AUTH_CACHE_PRFX, uname ); /**/ + + if(!seed) { + osrfMessageFree(omsg); + osrfAppSessionFree(session); + return osrfAppRequestRespondException( ctx->session, + ctx->request, "No authentication seed found. " + "open-ils.auth.authenticate.init must be called first"); + } + + osrfLog( OSRF_DEBUG, "oilsAuth retrieved seed from cache: %s", seed ); + char* maskedPw = md5sum( "%s%s", seed, realPassword ); + if(!maskedPw) return -1; + osrfLog( OSRF_DEBUG, "oilsAuth generated masked password %s. " + "Testing against provided password %s", maskedPw, password ); + + jsonObject* response; + + if( !strcmp( maskedPw, password ) ) { + + osrfLog( OSRF_INFO, "Login successful for %s", uname ); + char* string = va_list_to_string( "%d.%d.%s", getpid(), time(NULL), uname ); /**/ + char* authToken = md5sum(string); /**/ + char* authKey = va_list_to_string( "%s%s", OILS_AUTH_CACHE_PRFX, authToken ); /**/ + oilsFMSetString( userObj, "passwd", "" ); + osrfCachePutObject( authKey, userObj, 28800 ); /* XXX config value */ + response = jsonNewObject( authToken ); + free(string); free(authToken); free(authKey); + + } else { + osrfLog( OSRF_INFO, "Login failed for for %s", uname ); + response = jsonNewNumberObject(0); + } + + osrfAppRequestRespondComplete( ctx->session, ctx->request, response ); + jsonObjectFree(response); + osrfMessageFree(omsg); + osrfAppSessionFree(session); + + } else { + return osrfAppRequestRespondException( ctx->session, ctx->request, + "username and password required for method: %s", ctx->method->name ); + } + + return 0; + +} + +int oilsAuthSessionRetrieve( osrfMethodContext* ctx ) { + OSRF_METHOD_VERIFY_CONTEXT(ctx); + + char* authToken = jsonObjectGetString( jsonObjectGetIndex(ctx->params, 0)); + jsonObject* userObj = NULL; + + if( authToken ){ + char* key = va_list_to_string("%s%s", OILS_AUTH_CACHE_PRFX, authToken ); /**/ + userObj = osrfCacheGetObject( key ); /**/ + free(key); + } + + osrfAppRequestRespondComplete( ctx->session, ctx->request, userObj ); + jsonObjectFree(userObj); + return 0; +} + +int oilsAuthSessionDelete( osrfMethodContext* ctx ) { + OSRF_METHOD_VERIFY_CONTEXT(ctx); + + char* authToken = jsonObjectGetString( jsonObjectGetIndex(ctx->params, 0) ); + jsonObject* resp = NULL; + + if( authToken ) { + char* key = va_list_to_string("%s%s", OILS_AUTH_CACHE_PRFX, authToken ); /**/ + osrfCacheRemove(key); + resp = jsonNewObject(authToken); /**/ + free(key); + } + + osrfAppRequestRespondComplete( ctx->session, ctx->request, resp ); + jsonObjectFree(resp); + return 0; +} + + + diff --git a/Open-ILS/src/c-apps/oils_utils.c b/Open-ILS/src/c-apps/oils_utils.c new file mode 100644 index 0000000000..c2fe14743e --- /dev/null +++ b/Open-ILS/src/c-apps/oils_utils.c @@ -0,0 +1,25 @@ +#include "oils_utils.h" + +char* oilsFMGetString( jsonObject* object, char* field ) { + return jsonObjectToSimpleString(oilsFMGetObject( object, field )); +} + + +jsonObject* oilsFMGetObject( jsonObject* object, char* field ) { + if(!(object && field)) return NULL; + if( object->type != JSON_ARRAY || !object->classname ) return NULL; + int pos = fm_ntop(object->classname, field); + if( pos > -1 ) return jsonObjectGetIndex( object, pos ); + return NULL; +} + + +int oilsFMSetString( jsonObject* object, char* field, char* string ) { + if(!(object && field && string)) return -1; + int pos = fm_ntop(object->classname, field); + if( pos > -1 ) { + jsonObjectSetIndex( object, pos, jsonNewObject(string) ); + return 0; + } + return -1; +} diff --git a/Open-ILS/src/c-apps/oils_utils.h b/Open-ILS/src/c-apps/oils_utils.h new file mode 100644 index 0000000000..9c30bdc981 --- /dev/null +++ b/Open-ILS/src/c-apps/oils_utils.h @@ -0,0 +1,33 @@ +#include "objson/object.h" +#include "openils/fieldmapper_lookup.h" + +/** + Returns the string value for field 'field' in the given object. + This method calls jsonObjectToSimpleString so numbers will be + returned as strings. + @param object The object to inspect + @param field The field whose value is requsted + @return The string at the given position, if none exists, + then NULL is returned. The caller must free the returned string + */ +char* oilsFMGetString( jsonObject* object, char* field ); + + +/** + Returns the jsonObject found at the specified field in the + given object. + @param object The object to inspect + @param field The field whose value is requsted + @return The found object or NULL if none exists. Do NOT free the + returned object. + */ +jsonObject* oilsFMGetObject( jsonObject* object, char* field ); + +/** + Sets the given field in the given object to the given string + @param object The object to update + @param field The field to change + @param string The new data + @return 0 if the field was updated successfully, -1 on error + */ +int oilsFMSetString( jsonObject* object, char* field, char* string ); diff --git a/OpenSRF/bin/opensrf_all b/OpenSRF/bin/opensrf_all index 9f19e87a99..cdc998c5d4 100755 --- a/OpenSRF/bin/opensrf_all +++ b/OpenSRF/bin/opensrf_all @@ -125,7 +125,7 @@ function stopMe { sleep 1; echo "Stopping The Router..."; - killall opensrf_router; + killall "OpenSRF Router" sleep 1; diff --git a/OpenSRF/src/utils/utils.c b/OpenSRF/src/utils/utils.c index 0922544e41..9c42578540 100644 --- a/OpenSRF/src/utils/utils.c +++ b/OpenSRF/src/utils/utils.c @@ -397,16 +397,18 @@ char* file_to_string(const char* filename) { } -char* md5sum( char* text ) { +char* md5sum( char* text, ... ) { struct md5_ctx ctx; unsigned char digest[16]; MD5_start (&ctx); + VA_LIST_TO_STRING(text); + int i; - for ( i=0 ; i != strlen(text) ; i++ ) - MD5_feed (&ctx, text[i]); + for ( i=0 ; i != strlen(VA_BUF) ; i++ ) + MD5_feed (&ctx, VA_BUF[i]); MD5_stop (&ctx, digest); diff --git a/OpenSRF/src/utils/utils.h b/OpenSRF/src/utils/utils.h index a5ecb45a89..1737c29672 100644 --- a/OpenSRF/src/utils/utils.h +++ b/OpenSRF/src/utils/utils.h @@ -181,7 +181,7 @@ char* file_to_string(const char* filename); Calculates the md5 of the text provided. The returned string must be freed by the caller. */ -char* md5sum( char* text ); +char* md5sum( char* text, ... ); #endif diff --git a/install.sh b/install.sh index e6d0d288c3..a0573630ba 100755 --- a/install.sh +++ b/install.sh @@ -173,10 +173,12 @@ function runInstall { ;; "openils_core" ) + if building; then $MAKE -C "$OPENILSDIR" "c_apps"; fi; if installing; then $MAKE -C "$OPENILSDIR" "perl-install"; $MAKE -C "$OPENILSDIR" "string-templates-install"; $MAKE -C "$OPENILSDIR" "xsl-install"; + $MAKE -C "$OPENILSDIR" "c_apps-install"; fi; ;; -- 2.43.2