diff --git a/Project/Sources/Classes/OAuth2Authorization.4dm b/Project/Sources/Classes/OAuth2Authorization.4dm
new file mode 100644
index 0000000..f9e7b6d
--- /dev/null
+++ b/Project/Sources/Classes/OAuth2Authorization.4dm
@@ -0,0 +1,22 @@
+shared singleton Class constructor()
+
+Function getResponse($request : 4D.IncomingMessage) : 4D.OutgoingMessage
+
+ var $response:=4D.OutgoingMessage.new()
+ var $body : Blob
+ var $state : Text:=cs.Tools.me.getURLParameterValue($request.url; "state")
+ var $options : Object:={state: $state}
+ $options.redirectURI:=$request.urlPath
+ $options.result:=$request.getJSON()
+
+ If (_authorize($options; ->$body))
+
+ $response.setStatus(200)
+ $response.setHeader("Content-Type"; "text/html")
+ $response.setBody($body)
+ Else
+
+ $response.setStatus(404)
+ End if
+
+ return $response
diff --git a/Project/Sources/Classes/OAuth2Provider.4dm b/Project/Sources/Classes/OAuth2Provider.4dm
index 8aa56bf..6da73dd 100644
--- a/Project/Sources/Classes/OAuth2Provider.4dm
+++ b/Project/Sources/Classes/OAuth2Provider.4dm
@@ -30,7 +30,7 @@ property _grantType : Text
property _codeVerifier : Text
property _state : Text
-property enableDebugLog : Boolean // Enable HTTP Server debug log for Debug purposes only
+property enableDebugLog : Boolean // Enable HTTP Server debug log for Debug purposes only
Class constructor($inParams : Object)
@@ -496,7 +496,17 @@ Function _getToken_SignedIn($bUseRefreshToken : Boolean) : Object
End if
End if
- If (cs.Tools.me.startWebServer($options))
+ var $bUseHostDatabaseServer : Boolean:=False
+ var $hostDatabaseServer : Object:=WEB Server(Web server host database)
+ If (($hostDatabaseServer#Null)&& $hostDatabaseServer.isRunning)
+ If ($options.useTLS)
+ $bUseHostDatabaseServer:=($hostDatabaseServer.HTTPSEnabled && ($hostDatabaseServer.HTTPSPort=$options.port))
+ Else
+ $bUseHostDatabaseServer:=($hostDatabaseServer.HTTPEnabled && ($hostDatabaseServer.HTTPPort=$options.port))
+ End if
+ End if
+
+ If ($bUseHostDatabaseServer || cs.Tools.me.startWebServer($options))
var $authorizationCode : Text:=This._getAuthorizationCode()
diff --git a/Project/Sources/Classes/Tools.4dm b/Project/Sources/Classes/Tools.4dm
index d027d2e..148eab2 100644
--- a/Project/Sources/Classes/Tools.4dm
+++ b/Project/Sources/Classes/Tools.4dm
@@ -236,6 +236,28 @@ Function getJMAPAttribute($inKey : Text) : Text
// ----------------------------------------------------
+Function getDomainFromURL($URL : Text) : Text
+
+ ARRAY LONGINT($pos; 0)
+ ARRAY LONGINT($len; 0)
+
+ var $result : Text
+ var $pattern : Text:="(?mi-s)^(https?|wss?)://(.*)(:\\d*)(/?.*)"
+
+ If (Match regex($pattern; $URL; 1; $pos; $len))
+
+ If (Size of array($pos)>2)
+ $result:=Substring($URL; $pos{3}+1; $len{3}-1)
+ End if
+
+ End if
+
+ return $result
+
+
+ // ----------------------------------------------------
+
+
Function getPathFromURL($URL : Text) : Text
ARRAY LONGINT($pos; 0)
@@ -341,6 +363,35 @@ Function isEmailAddressHeader($inKey : Text) : Boolean
// ----------------------------------------------------
+Function isLocalIP($inIPAddress : Text) : Boolean
+
+ If (Length($inIPAddress)=0)
+ return False
+ End if
+ If (($inIPAddress="127.0.0.1") || ($inIPAddress="::1") || ($inIPAddress="localhost"))
+ return True
+ End if
+
+ var $sysInfo : Object:=System info
+ var $networkInterfaces : Collection:=$sysInfo.networkInterfaces
+ var $networkInterface : Object
+
+ For each ($networkInterface; $networkInterfaces)
+ var $ipAddresses : Collection:=$networkInterface.ipAddresses
+ var $ipAddress : Object
+ For each ($ipAddress; $ipAddresses)
+ If ($ipAddress.ip=$inIPAddress)
+ return True
+ End if
+ End for each
+ End for each
+
+ return False
+
+
+ // ----------------------------------------------------
+
+
Function isValidEmail($inEmail : Text) : Boolean
var $pattern : Text:="(?i)^[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$"
@@ -350,23 +401,23 @@ Function isValidEmail($inEmail : Text) : Boolean
// ----------------------------------------------------
-Function quoteString($inString : text) : text
+Function quoteString($inString : Text) : Text
var $result : Text:=$inString
var $length : Integer:=Length($result)
-
- if($length>0)
- if ($result[[1]]#"\"")
+
+ If ($length>0)
+ If ($result[[1]]#"\"")
$result:="\""+$result
- End if
+ End if
If ($result[[$length]]#"\"")
$result+="\""
- End if
- End if
-
+ End if
+ End if
+
return $result
-
-
+
+
// ----------------------------------------------------
@@ -545,6 +596,6 @@ Function urlEncode($value : Text) : Text
Function localizedString($inValue : Text) : Text
-
- /* Temp to avoid compilation issues due to command renaming */
- return Localized string:C991($inValue)
+
+/* Temp to avoid compilation issues due to command renaming */
+ return Localized string:C991($inValue)
\ No newline at end of file
diff --git a/Project/Sources/Methods/_authorize.4dm b/Project/Sources/Methods/_authorize.4dm
new file mode 100644
index 0000000..3c7c9a6
--- /dev/null
+++ b/Project/Sources/Methods/_authorize.4dm
@@ -0,0 +1,76 @@
+//%attributes = {"invisible":true}
+#DECLARE($inOptions : Object; $outResponseBodyPtr : Pointer) : Boolean
+
+var $redirectURI : Text
+var $URL : Text:=$inOptions.redirectURI
+var $customResponseFile; $customErrorFile : 4D.File
+var $state : Text:=String($inOptions.state)
+var $responseFile : 4D.File:=Folder(fk resources folder).file("Response_Template.html")
+
+If (OB Is defined(Storage.requests; $state))
+ $redirectURI:=String(Storage.requests[$state].redirectURI)
+ If (Length($redirectURI)>0)
+ $redirectURI:=cs.Tools.me.getPathFromURL($redirectURI)+"@"
+ End if
+ $customResponseFile:=(Value type(Storage.requests[$state].authenticationPage)#Is undefined) ? Storage.requests[$state].authenticationPage : Null
+ $customErrorFile:=(Value type(Storage.requests[$state].authenticationErrorPage)#Is undefined) ? Storage.requests[$state].authenticationErrorPage : Null
+End if
+
+If ($URL=$redirectURI)
+
+ var $pageTitle; $pageMessage; $pageDetails : Text
+
+ If (OB Is defined(Storage.requests; $state))
+ Use (Storage.requests[$state])
+ Storage.requests[$state].token:=$inOptions.result
+ End use
+ End if
+
+ If (($inOptions.result=Null) | (OB Is defined($inOptions.result; "error")))
+
+ $pageTitle:=cs.Tools.me.localizedString("OAuth2_Response_Title")
+ $pageMessage:=cs.Tools.me.localizedString("OAuth2_Error_Message")
+
+ If (OB Is defined($inOptions.result; "error"))
+ $pageMessage+=("
"+String($inOptions.result.error))
+ End if
+ If (OB Is defined($inOptions.result; "error_subtype"))
+ $pageMessage+=("
"+String($inOptions.result.error_subtype))
+ End if
+ If (OB Is defined($inOptions.result; "error_description"))
+ $pageMessage+=("
"+String($inOptions.result.error_description))
+ End if
+ If (OB Is defined($inOptions.result; "error_uri"))
+ $pageMessage+=("
"+String($inOptions.result.error_uri))
+ End if
+ $pageDetails:=cs.Tools.me.localizedString("OAuth2_Response_Details")
+
+ $responseFile:=($customErrorFile#Null) ? $customErrorFile : $responseFile
+ Else
+
+ $pageTitle:=cs.Tools.me.localizedString("OAuth2_Response_Title")
+ $pageMessage:=cs.Tools.me.localizedString("OAuth2_Response_Message")
+ $pageDetails:=cs.Tools.me.localizedString("OAuth2_Response_Details")
+
+ $responseFile:=($customResponseFile#Null) ? $customResponseFile : $responseFile
+ End if
+
+ var $responseFileContent : Text:=$responseFile.getText()
+ var $outResponseBody : Text:=""
+
+ PROCESS 4D TAGS($responseFileContent; $outResponseBody; $pageTitle; $pageMessage; $pageDetails)
+
+ If (Type($outResponseBodyPtr)=Is pointer)
+ Case of
+ : (Type($outResponseBodyPtr->)=Is text)
+ $outResponseBodyPtr->:=$outResponseBody
+ : (Type($outResponseBodyPtr->)=Is BLOB)
+ CONVERT FROM TEXT($outResponseBody; "UTF-8"; $outResponseBodyPtr->)
+ End case
+ End if
+
+ return True
+
+End if
+
+return False
diff --git a/Project/Sources/Methods/_onWebConnection.4dm b/Project/Sources/Methods/_onWebConnection.4dm
index 15dfde4..f77649b 100644
--- a/Project/Sources/Methods/_onWebConnection.4dm
+++ b/Project/Sources/Methods/_onWebConnection.4dm
@@ -2,24 +2,19 @@
#DECLARE($URL : Text; $header : Text; $peerIP : Text; $localIP : Text; $username : Text; $password : Text)
var $redirectURI : Text
-var $customResponseFile; $customErrorFile : 4D.File
var $state : Text:=cs.Tools.me.getURLParameterValue($1; "state")
-var $responseFile : 4D.File:=Folder(fk resources folder).file("Response_Template.html")
If (OB Is defined(Storage.requests; $state))
$redirectURI:=String(Storage.requests[$state].redirectURI)
If (Length($redirectURI)>0)
$redirectURI:=cs.Tools.me.getPathFromURL($redirectURI)+"@"
End if
- $customResponseFile:=(Value type(Storage.requests[$state].authenticationPage)#Is undefined) ? Storage.requests[$state].authenticationPage : Null
- $customErrorFile:=(Value type(Storage.requests[$state].authenticationErrorPage)#Is undefined) ? Storage.requests[$state].authenticationErrorPage : Null
End if
If ($URL=$redirectURI)
- var $result : Object
- var WSTITLE; WSMESSAGE; WSDETAILS : Text
-
+ var $options : Object:={redirectURI: $redirectURI; state: $state}
+
ARRAY TEXT($names; 0)
ARRAY TEXT($values; 0)
WEB GET VARIABLES($names; $values)
@@ -27,54 +22,23 @@ If ($URL=$redirectURI)
If (Size of array($names)>0)
var $i : Integer
- $result:=New shared object
+ var $result : Object:=New shared object
Use ($result)
For ($i; 1; Size of array($names))
$result[$names{$i}]:=$values{$i}
End for
End use
-
+ $options.result:=$result
End if
- If (OB Is defined(Storage.requests; $state))
- Use (Storage.requests[$state])
- Storage.requests[$state].token:=$result
- End use
- End if
-
- If (($result=Null) | (OB Is defined($result; "error")))
-
- WSTITLE:=cs.Tools.me.localizedString("OAuth2_Response_Title")
- WSMESSAGE:=cs.Tools.me.localizedString("OAuth2_Error_Message")
+ var $responseBody : Blob
+ If (_authorize($options; ->$responseBody))
- If (OB Is defined($result; "error"))
- WSMESSAGE:=WSMESSAGE+"
"+$result.error
- End if
- If (OB Is defined($result; "error_subtype"))
- WSMESSAGE:=WSMESSAGE+"
"+$result.error_subtype
- End if
- If (OB Is defined($result; "error_description"))
- WSMESSAGE:=WSMESSAGE+"
"+$result.error_description
- End if
- If (OB Is defined($result; "error_uri"))
- WSMESSAGE:=WSMESSAGE+"
"+$result.error_uri
- End if
- WSDETAILS:=cs.Tools.me.localizedString("OAuth2_Response_Details")
-
- $responseFile:=($customErrorFile#Null) ? $customErrorFile : $responseFile
- Else
-
- WSTITLE:=cs.Tools.me.localizedString("OAuth2_Response_Title")
- WSMESSAGE:=cs.Tools.me.localizedString("OAuth2_Response_Message")
- WSDETAILS:=cs.Tools.me.localizedString("OAuth2_Response_Details")
-
- $responseFile:=($customResponseFile#Null) ? $customResponseFile : $responseFile
+ var $contentType : Text:="Content-Type: text/html"
+ WEB SET HTTP HEADER($contentType)
+ WEB SEND RAW DATA($responseBody)
End if
- WEB SEND FILE($responseFile.platformPath)
-
-Else
-
- // Nothing to do... 404 will be automatically sent
-
End if
+
+// Nothing to do... 404 will be automatically sent
diff --git a/Resources/Response_Template.html b/Resources/Response_Template.html
index 92a47b1..4090003 100644
--- a/Resources/Response_Template.html
+++ b/Resources/Response_Template.html
@@ -14,7 +14,7 @@