fidor_starter_kits 0.3.3 → 0.3.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +7 -2
- data/README.md +4 -5
- data/lib/fidor_starter_kits/version.rb +2 -2
- data/lib/fidor_starter_kits.rb +4 -4
- data/spec/fidor_starter_kits_spec.rb +7 -7
- data/starter_kits/golang_plain/example.go +170 -91
- data/starter_kits/node_tx/example.js +246 -40
- data/starter_kits/{php_plain → php_oauth_plain}/.fidor_meta.json +2 -2
- data/starter_kits/{php_plain → php_oauth_plain}/README.md +1 -1
- data/starter_kits/{php_plain → php_oauth_plain}/example.php +12 -13
- data/starter_kits/ruby_oauth_plain/.fidor_meta.json +7 -0
- data/starter_kits/{sinatra_plain → ruby_oauth_plain}/Gemfile +1 -2
- data/starter_kits/{sinatra_plain → ruby_oauth_plain}/README.md +2 -2
- data/starter_kits/ruby_oauth_plain/example.rb +39 -0
- metadata +9 -9
- data/starter_kits/sinatra_plain/.fidor_meta.json +0 -7
- data/starter_kits/sinatra_plain/example.rb +0 -40
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0d9257e8f3fd57a085a5bfad18e7d08e17f0410d
|
4
|
+
data.tar.gz: 6cc26babb8d847a711d48556b3285b3a3543cb70
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 475514d665725df63f3c2047df7b0dd7878f0c8b838045f80603829a938d0e1f4f3dc4e32a05e04e1edee4c9c9d24b5684a323e5c035b8c7fa7a30d9e6e1e101
|
7
|
+
data.tar.gz: effb9982ec4dea6dab0b50460f6c527b72686259dad4ff31d71d63a8a48a178ccf3e802d36bc8034142174ddf44b3052c22a33085d6bbd0efb4d24d80ff5d30a
|
data/CHANGELOG.md
CHANGED
@@ -1,8 +1,13 @@
|
|
1
1
|
# Changelog Fidor Admin API Schema
|
2
2
|
See [commit messages](https://github.com/fidor/fidor_starter_kits/commits/) for details.
|
3
3
|
|
4
|
-
##2015-
|
5
|
-
|
4
|
+
##2015-06
|
5
|
+
|
6
|
+
* fix usage of access_token in api URLs, now set in Authorization Header
|
7
|
+
|
8
|
+
##2015-01
|
9
|
+
|
10
|
+
*fix proper TLS handling for node example
|
6
11
|
|
7
12
|
##2014-12
|
8
13
|
|
data/README.md
CHANGED
@@ -11,7 +11,6 @@ information into the source files and delivers the example as zipped download.
|
|
11
11
|
If you choose the manual way to explore our example apps, simply checkout this
|
12
12
|
repo, register and app and add the required credentials, URL's to the sources.
|
13
13
|
|
14
|
-
|
15
14
|
For Ruby Heros, this repo is also available as ruby gem and provides a tiny
|
16
15
|
helper for app creation, see Install & Usage.
|
17
16
|
|
@@ -57,18 +56,18 @@ application manager. Before the following placeholders inside in your main
|
|
57
56
|
example.xy file are substituted with the according values from the app
|
58
57
|
(client_id/secret) and the values in .fidor_meta.json:
|
59
58
|
|
60
|
-
<APP_URL>
|
59
|
+
<APP_URL> # default http://localhost:8000/example.php
|
61
60
|
<CLIENT_ID>
|
62
61
|
<CLIENT_SECRET>
|
63
|
-
<FIDOR_OAUTH_URL>
|
64
|
-
<FIDOR_API_URL>
|
62
|
+
<FIDOR_OAUTH_URL> # e.g Sandbox: https://aps.fidor.de/oauth / Live: https://apm.fidor.de/oauth
|
63
|
+
<FIDOR_API_URL> # e.g Sandbox: https://aps.fidor.de / Live: https://api.fidor.de
|
65
64
|
|
66
65
|
So just add those to example.[rb, php, ..] and see existing examples and specs
|
67
66
|
for a reference.
|
68
67
|
|
69
68
|
## Contributing
|
70
69
|
|
71
|
-
1. Fork it (
|
70
|
+
1. Fork it (https://github.com/fidor/fidor_starter_kits/fork )
|
72
71
|
2. Create your feature branch (`git checkout -b my-new-feature`)
|
73
72
|
3. Commit your changes (`git commit -am 'Add some feature'`)
|
74
73
|
4. Push to the branch (`git push origin my-new-feature`)
|
@@ -1,3 +1,3 @@
|
|
1
1
|
module FidorStarterKits
|
2
|
-
VERSION = '0.3.
|
3
|
-
end
|
2
|
+
VERSION = '0.3.5'
|
3
|
+
end
|
data/lib/fidor_starter_kits.rb
CHANGED
@@ -6,7 +6,7 @@ require 'json'
|
|
6
6
|
|
7
7
|
module FidorStarterKits
|
8
8
|
|
9
|
-
STARTER_KITS = %w{ node_tx golang_plain
|
9
|
+
STARTER_KITS = %w{ node_tx golang_plain php_oauth_plain ruby_oauth_plain java_servlet }
|
10
10
|
|
11
11
|
class << self
|
12
12
|
|
@@ -70,7 +70,7 @@ module FidorStarterKits
|
|
70
70
|
if File.exists? meta
|
71
71
|
File.open(meta) {|f| @conf[kit] = JSON.parse(f.read)}
|
72
72
|
else
|
73
|
-
@conf[kit] = "
|
73
|
+
@conf[kit] = {"error" => ".fidor_meta.json not found"}
|
74
74
|
end
|
75
75
|
end
|
76
76
|
return @conf
|
@@ -80,8 +80,8 @@ module FidorStarterKits
|
|
80
80
|
all[app_name]
|
81
81
|
end
|
82
82
|
|
83
|
-
def each
|
84
|
-
all.each_value { |conf| yield conf }
|
83
|
+
def each
|
84
|
+
all.each_value { |conf| yield conf }
|
85
85
|
end
|
86
86
|
|
87
87
|
end
|
@@ -4,10 +4,10 @@ describe FidorStarterKits do
|
|
4
4
|
|
5
5
|
describe '.exists?' do
|
6
6
|
it 'is true' do
|
7
|
-
expect( FidorStarterKits.exists?('
|
7
|
+
expect( FidorStarterKits.exists?('ruby_oauth_plain') ).to be
|
8
8
|
end
|
9
9
|
it 'is false' do
|
10
|
-
expect( FidorStarterKits.exists?('
|
10
|
+
expect( FidorStarterKits.exists?('ruby_oauth_plain') ).to be
|
11
11
|
end
|
12
12
|
end
|
13
13
|
|
@@ -21,7 +21,7 @@ describe FidorStarterKits do
|
|
21
21
|
|
22
22
|
it 'creates zip file' do
|
23
23
|
opts = {
|
24
|
-
app_name: '
|
24
|
+
app_name: 'ruby_oauth_plain',
|
25
25
|
client_id: '123',
|
26
26
|
client_secret: '12345',
|
27
27
|
app_url: 'localhost'
|
@@ -32,7 +32,7 @@ describe FidorStarterKits do
|
|
32
32
|
|
33
33
|
it 'replaces placeholders in example.rb' do
|
34
34
|
opts = {
|
35
|
-
app_name: '
|
35
|
+
app_name: 'ruby_oauth_plain',
|
36
36
|
client_id: 'my-client-id',
|
37
37
|
client_secret: 'my-client-secret',
|
38
38
|
app_url: 'my-app-url',
|
@@ -49,7 +49,7 @@ describe FidorStarterKits do
|
|
49
49
|
end
|
50
50
|
end
|
51
51
|
|
52
|
-
describe '.all' do
|
52
|
+
describe '.all' do
|
53
53
|
it 'lists all starter kits' do
|
54
54
|
expect(FidorStarterKits.all.count).to eq(FidorStarterKits::STARTER_KITS.size)
|
55
55
|
end
|
@@ -58,8 +58,8 @@ describe FidorStarterKits do
|
|
58
58
|
conf = FidorStarterKits.all
|
59
59
|
expect(conf["golang_plain"]["display_name"]).to eq("Go Plain")
|
60
60
|
expect(conf["node_tx"]["description"]).to eq("A simple nodejs based app, showing how to get user transactions")
|
61
|
-
expect(conf["
|
62
|
-
expect(conf["
|
61
|
+
expect(conf["php_oauth_plain"]["app_name"]).to eq("php_oauth_plain")
|
62
|
+
expect(conf["ruby_oauth_plain"]["app_url"]).to eq("http://localhost:4567")
|
63
63
|
expect(conf["java_servlet"]["callback_urls"]).to eq("http://localhost:8080/JavaServlet/Example")
|
64
64
|
end
|
65
65
|
end
|
@@ -12,78 +12,189 @@ package main
|
|
12
12
|
// $ http://localhost:8080
|
13
13
|
|
14
14
|
import (
|
15
|
+
"crypto/rand"
|
16
|
+
"encoding/hex"
|
15
17
|
"encoding/json"
|
18
|
+
"errors"
|
16
19
|
"fmt"
|
20
|
+
"io"
|
17
21
|
"net/http"
|
18
22
|
"net/url"
|
19
|
-
"
|
23
|
+
"strings"
|
20
24
|
)
|
21
25
|
|
22
26
|
// The following sections define the settings you require for the
|
23
27
|
// app to be able to connect to and authorize itself against the api.
|
24
28
|
|
25
|
-
|
26
|
-
//
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
//
|
31
|
-
|
32
|
-
// The OAuth Endpoint this App provides
|
33
|
-
var oauth_cb_url = "<APP_URL>"
|
34
|
-
|
35
|
-
// The URL of the Fidor API (this changes between Sandbox and
|
36
|
-
// Production)
|
37
|
-
var fidor_api_url = "<FIDOR_API_URL>" // e.g https://fidor.com/api_sandbox vs /api
|
38
|
-
|
39
|
-
|
29
|
+
type Config struct {
|
30
|
+
AppUrl string // where to reach this application
|
31
|
+
ClientId string // OAuth Client_id parameter
|
32
|
+
ClientSecret string // OAuth Client_secret parameter
|
33
|
+
FidorApiUrl string // API endpoint (this changes between Sandbox and Production)
|
34
|
+
FidorOauthUrl string // OAuth endpoint (this changes between Sandbox and Production)
|
35
|
+
}
|
40
36
|
|
37
|
+
var fidorConfig = Config{
|
38
|
+
AppUrl: "<APP_URL>",
|
39
|
+
ClientId: "<CLIENT_ID>",
|
40
|
+
ClientSecret: "<CLIENT_SECRET>",
|
41
|
+
FidorApiUrl: "<FIDOR_API_URL>",
|
42
|
+
FidorOauthUrl: "<FIDOR_OAUTH_URL>",
|
43
|
+
}
|
41
44
|
|
42
45
|
func main() {
|
43
46
|
// register a handler function (see next function) to service
|
44
47
|
// requests ...
|
45
48
|
http.HandleFunc("/", indexHandler)
|
46
|
-
fmt.Printf("Now open
|
49
|
+
fmt.Printf("Now open %s\n", fidorConfig.AppUrl)
|
47
50
|
// ... and start listening.
|
48
|
-
|
51
|
+
if u, err := url.Parse(fidorConfig.AppUrl); err != nil {
|
52
|
+
fmt.Printf("Can't make sense of configured url: %s\nBye.\n", fidorConfig.AppUrl)
|
53
|
+
} else {
|
54
|
+
var hostPort = strings.Split(u.Host, ":")
|
55
|
+
var port = ":8080"
|
56
|
+
if len(hostPort) == 2 {
|
57
|
+
port = ":" + hostPort[1]
|
58
|
+
}
|
59
|
+
http.ListenAndServe(port, nil)
|
60
|
+
}
|
49
61
|
}
|
50
62
|
|
51
63
|
func indexHandler(w http.ResponseWriter, r *http.Request) {
|
64
|
+
if r.Method != "GET" {
|
65
|
+
w.WriteHeader(403)
|
66
|
+
return
|
67
|
+
}
|
52
68
|
|
53
|
-
|
54
|
-
|
69
|
+
switch r.URL.Path {
|
70
|
+
case "/":
|
71
|
+
renderWelcome(w)
|
72
|
+
case "/transactions":
|
73
|
+
render("/transactions", w, r)
|
74
|
+
case "/accounts":
|
75
|
+
render("/accounts", w, r)
|
76
|
+
case "/oauth":
|
77
|
+
handleOAuthCallback(w, r)
|
78
|
+
case "/logout":
|
79
|
+
handleLogout(w, r, "/")
|
80
|
+
default:
|
55
81
|
w.WriteHeader(404)
|
56
|
-
return
|
57
82
|
}
|
83
|
+
}
|
84
|
+
|
85
|
+
const COOKIE_NAME = "GO_SESSION"
|
86
|
+
|
87
|
+
// session database, available access_tokens are mapped to their cookie-session keys
|
88
|
+
var sessions = make(map[string]string)
|
89
|
+
|
90
|
+
// stores a retireved access_token both on the server and the reference in a client-side cookie.
|
91
|
+
func createSession(w http.ResponseWriter, accessToken string) {
|
92
|
+
println(accessToken)
|
93
|
+
rnd := make([]byte, 20, 20)
|
94
|
+
rand.Read(rnd)
|
95
|
+
session := hex.EncodeToString(rnd)
|
96
|
+
sessions[session] = accessToken
|
97
|
+
cookie := http.Cookie{
|
98
|
+
Name: COOKIE_NAME,
|
99
|
+
Value: session,
|
100
|
+
}
|
101
|
+
http.SetCookie(w, &cookie)
|
102
|
+
}
|
103
|
+
|
104
|
+
// proxies an API endpoint. In case the client is not logged in (i.e. no
|
105
|
+
// session cookie is set), the OAuth procedure is initiated. Once the
|
106
|
+
// client is logged, a call the the `endpoint` API endpoint is made and
|
107
|
+
// the results (including errors) are piped to the client.
|
108
|
+
func render(endpoint string, w http.ResponseWriter, r *http.Request) {
|
109
|
+
// check if request has cookie set
|
110
|
+
if cookie, err := r.Cookie(COOKIE_NAME); err != nil {
|
111
|
+
// else redirect to OAuth Authorization EP
|
112
|
+
redirectToOAuth(w, r, endpoint)
|
113
|
+
} else {
|
114
|
+
session := cookie.Value
|
115
|
+
accessToken := sessions[session]
|
58
116
|
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
if values["code"] != nil {
|
63
|
-
// retrieve the actual OAuth access token ....
|
64
|
-
code := values.Get("code")
|
65
|
-
if token, err := retrieveTokenFromCode(code); err != nil {
|
66
|
-
fmt.Printf("err: %v\n", err)
|
117
|
+
// pipe api endpoint
|
118
|
+
ep := fmt.Sprintf("%s/%s", fidorConfig.FidorApiUrl, endpoint)
|
119
|
+
if api_req, err := http.NewRequest("GET", ep, nil); err != nil {
|
67
120
|
w.WriteHeader(500)
|
68
|
-
|
121
|
+
w.Write([]byte(err.Error()))
|
69
122
|
} else {
|
70
|
-
|
71
|
-
|
123
|
+
api_req.Header.Set("Authorization", fmt.Sprintf("Bearer %s", accessToken))
|
124
|
+
|
125
|
+
client := &http.Client{}
|
126
|
+
if api_resp, err := client.Do(api_req); err != nil {
|
127
|
+
w.WriteHeader(500)
|
128
|
+
w.Write([]byte(err.Error()))
|
129
|
+
} else {
|
130
|
+
if api_resp.StatusCode == 401 { // token probably expired
|
131
|
+
handleLogout(w, r, endpoint)
|
132
|
+
return
|
133
|
+
}
|
134
|
+
contentType := http.CanonicalHeaderKey("content-type")
|
135
|
+
w.Header().Set(contentType, api_resp.Header.Get(contentType))
|
136
|
+
w.WriteHeader(api_resp.StatusCode)
|
137
|
+
io.Copy(w, api_resp.Body)
|
138
|
+
}
|
72
139
|
}
|
140
|
+
}
|
141
|
+
}
|
142
|
+
|
143
|
+
// client browser is redirected to `authorize` oauth endpoints. The
|
144
|
+
// `target_endpoint` parameter indicates which application endpoint to
|
145
|
+
// redirect the client to once the access_token has been retrieved.
|
146
|
+
func redirectToOAuth(w http.ResponseWriter, r *http.Request, target_endpoint string) {
|
147
|
+
_redirectURI := fmt.Sprintf("%s/oauth?ep=%s", fidorConfig.AppUrl, target_endpoint)
|
148
|
+
redirectURI := url.QueryEscape(_redirectURI)
|
149
|
+
|
150
|
+
oauthRedirectURL := fmt.Sprintf("%s/authorize?client_id=%s&state=321&response_type=code&redirect_uri=%s", fidorConfig.FidorOauthUrl, fidorConfig.ClientId, redirectURI)
|
151
|
+
http.Redirect(w, r, oauthRedirectURL, 307)
|
152
|
+
}
|
153
|
+
|
154
|
+
// handles the oauth callback (i.e. the redirect that the oauth
|
155
|
+
// authorize call "returns" to the client)
|
156
|
+
func handleOAuthCallback(w http.ResponseWriter, r *http.Request) {
|
157
|
+
code := r.FormValue("code")
|
158
|
+
target := r.FormValue("ep")
|
159
|
+
|
160
|
+
if code == "" || target == "" {
|
161
|
+
w.WriteHeader(500)
|
162
|
+
w.Write([]byte("missing code or target ep"))
|
163
|
+
return
|
164
|
+
}
|
165
|
+
|
166
|
+
if token, err := retrieveTokenFromCode(code, target); err != nil {
|
167
|
+
w.WriteHeader(500)
|
168
|
+
w.Write([]byte(err.Error()))
|
169
|
+
return
|
73
170
|
} else {
|
74
|
-
|
75
|
-
|
76
|
-
oauth_url := fmt.Sprintf("%s/authorize?client_id=%s&state=123&response_type=code&redirect_uri=%s",
|
77
|
-
fidor_oauth_url,
|
78
|
-
client_id,
|
79
|
-
url.QueryEscape(oauth_cb_url))
|
80
|
-
|
81
|
-
header := w.Header()
|
82
|
-
header.Add("location", oauth_url)
|
83
|
-
w.WriteHeader(307)
|
171
|
+
createSession(w, token)
|
172
|
+
http.Redirect(w, r, target, 307)
|
84
173
|
}
|
85
174
|
}
|
86
175
|
|
176
|
+
// clear our application's session, forces user to call the oauth
|
177
|
+
// authorize endpoint again. This may or may not force the user to have
|
178
|
+
// to reenter credentials, depending on whether the user's Fidor session
|
179
|
+
// has expired.
|
180
|
+
func handleLogout(w http.ResponseWriter, r *http.Request, endpoint string) {
|
181
|
+
if cookie, err := r.Cookie(COOKIE_NAME); err == nil {
|
182
|
+
// we have a cookie
|
183
|
+
|
184
|
+
// remove it from our stored sessions
|
185
|
+
session := cookie.Value
|
186
|
+
delete(sessions, session)
|
187
|
+
|
188
|
+
// kill the cookie on the client
|
189
|
+
cookie := http.Cookie{
|
190
|
+
Name: COOKIE_NAME,
|
191
|
+
Value: "",
|
192
|
+
MaxAge: -1,
|
193
|
+
}
|
194
|
+
http.SetCookie(w, &cookie)
|
195
|
+
}
|
196
|
+
http.Redirect(w, r, endpoint, 307)
|
197
|
+
}
|
87
198
|
|
88
199
|
// Our TokenResponse representation used to pick it out from the JSON
|
89
200
|
// returned by the OAuth server.
|
@@ -92,18 +203,22 @@ type TokenResponse struct {
|
|
92
203
|
}
|
93
204
|
|
94
205
|
// Use the OAuth code that the user's browser picked up from the OAuth
|
95
|
-
// server to request an OAuth access_token to use in API requests.
|
96
|
-
|
206
|
+
// server to request an OAuth access_token to use in API requests. The
|
207
|
+
// `target_endpoint` parameter indicates which of this app's endpoints
|
208
|
+
// to redirect the client to once we have the access_token and stored a
|
209
|
+
// reference in the client's cookie.
|
210
|
+
func retrieveTokenFromCode(code string, target_endpoint string) (token string, err error) {
|
97
211
|
// assemble the API endpoint URL and request payload
|
98
|
-
|
212
|
+
redirect_uri := fmt.Sprintf("%s/oauth?ep=%s", fidorConfig.AppUrl, target_endpoint)
|
99
213
|
tokenPayload := url.Values{
|
100
|
-
"client_id": {
|
101
|
-
"client_secret": {
|
214
|
+
"client_id": {fidorConfig.ClientId},
|
215
|
+
"client_secret": {fidorConfig.ClientSecret},
|
102
216
|
"code": {code},
|
103
|
-
"redirect_uri": {url.QueryEscape(
|
217
|
+
"redirect_uri": {url.QueryEscape(redirect_uri)},
|
104
218
|
"grant_type": {"authorization_code"},
|
105
219
|
}
|
106
|
-
// Call
|
220
|
+
// Call the Oauth `token` endpoint
|
221
|
+
tokenUrl := fmt.Sprintf("%s/token", fidorConfig.FidorOauthUrl)
|
107
222
|
if resp, err := http.PostForm(tokenUrl, tokenPayload); err != nil {
|
108
223
|
println(err)
|
109
224
|
return "", err
|
@@ -122,44 +237,8 @@ func retrieveTokenFromCode(code string) (token string, err error) {
|
|
122
237
|
}
|
123
238
|
}
|
124
239
|
|
125
|
-
|
126
|
-
|
127
|
-
// information. This is our internal representation of the returned JSON
|
128
|
-
// used to pick out the user's email.
|
129
|
-
type UserResponse struct {
|
130
|
-
Email string `json:"email"`
|
131
|
-
}
|
132
|
-
|
133
|
-
// function to retrieve user information from the API
|
134
|
-
func getUser(token string) (u UserResponse, err error) {
|
135
|
-
// Assemble endpoint URL...
|
136
|
-
url := fmt.Sprintf("%s/users/current?access_token=%s", fidor_api_url, token)
|
137
|
-
if resp, err := http.Get(url); err != nil {
|
138
|
-
return u, err
|
139
|
-
} else {
|
140
|
-
decoder := json.NewDecoder(resp.Body)
|
141
|
-
if err = decoder.Decode(&u); err != nil {
|
142
|
-
return u, err
|
143
|
-
} else {
|
144
|
-
return u, nil
|
145
|
-
}
|
146
|
-
}
|
147
|
-
}
|
148
|
-
|
149
|
-
|
150
|
-
// once all the OAuth calls have been taken care of, this function is
|
151
|
-
// called from the http handler. It retrieves the user's email address
|
152
|
-
// and inserts links to `transaction` and `accounts` endpoints.
|
153
|
-
|
154
|
-
func renderWelcome(w http.ResponseWriter, token string) {
|
155
|
-
if user, err := getUser(token); err != nil {
|
156
|
-
fmt.Printf("err: %v\n", err)
|
157
|
-
w.WriteHeader(500)
|
158
|
-
} else {
|
159
|
-
txLink := fmt.Sprintf("%s/transactions?access_token=%s", fidor_api_url, token)
|
160
|
-
acctsLink := fmt.Sprintf("%s/accounts?access_token=%s", fidor_api_url, token)
|
161
|
-
fmt.Fprintf(w, indexTemplate, user.Email, token, txLink, acctsLink)
|
162
|
-
}
|
240
|
+
func renderWelcome(w http.ResponseWriter) {
|
241
|
+
w.Write([]byte(indexTemplate))
|
163
242
|
}
|
164
243
|
|
165
244
|
var indexTemplate = `
|
@@ -167,10 +246,10 @@ var indexTemplate = `
|
|
167
246
|
<head>
|
168
247
|
</head>
|
169
248
|
<body>
|
170
|
-
<h1>Welcome
|
171
|
-
<
|
172
|
-
<p><a href="
|
173
|
-
<p><a href="
|
249
|
+
<h1>Welcome!</h1>
|
250
|
+
<p><a href="/transactions">Transactions</a></p>
|
251
|
+
<p><a href="/accounts">Accounts</a></p>
|
252
|
+
<p><a href="/logout">Log Out</a></p>
|
174
253
|
</body>
|
175
254
|
</html>
|
176
255
|
`
|
@@ -4,35 +4,49 @@
|
|
4
4
|
//
|
5
5
|
// This sample intentionally does not require any further dependencies.
|
6
6
|
// We tried to keep things as simple as possible in order to illustrate the
|
7
|
-
// underlying mechanisms of the API.
|
7
|
+
// underlying mechanisms of the API. This comes at the expense of having
|
8
|
+
// to handled cookies and session in the sample...
|
8
9
|
//
|
9
10
|
// Using this code
|
10
11
|
// ---------------
|
11
12
|
//
|
13
|
+
// The provided source code is divided into three sections:
|
14
|
+
// 1.) Handling OAuth calls
|
15
|
+
// 2.) Cookie and Session Handling
|
16
|
+
// 3.) Handling Browser Requests
|
17
|
+
//
|
12
18
|
// In order to use this code, a sample app needs to be installed in the
|
13
19
|
// Fidor App Manager. Settings for this app are displayed in the app
|
14
|
-
// manager an need to be transfered into the config below
|
20
|
+
// manager an need to be transfered into the config below, if you
|
21
|
+
// downloaded the code directly from the Fidor App Manager, these
|
22
|
+
// settings should be filled in for you:
|
15
23
|
|
16
24
|
var fidor_config = {
|
17
25
|
app_url : "<APP_URL>",
|
18
26
|
client_id : "<CLIENT_ID>",
|
19
27
|
client_secret : "<CLIENT_SECRET>",
|
20
|
-
fidor_api_url : "<FIDOR_API_URL>"
|
28
|
+
fidor_api_url : "<FIDOR_API_URL>",
|
29
|
+
fidor_oauth_url: "<FIDOR_OAUTH_URL>"
|
21
30
|
}
|
22
31
|
|
23
32
|
|
33
|
+
/************************************************************************
|
34
|
+
/* BEGIN: OAuth Calls
|
35
|
+
************************************************************************/
|
24
36
|
|
25
|
-
|
37
|
+
//
|
26
38
|
// redirect the user to the OAuth authorization endpoint with the
|
27
39
|
// following params:
|
28
40
|
// - client_id
|
29
41
|
// - state
|
30
42
|
// - response_type
|
31
43
|
// - redirect_uri
|
32
|
-
|
33
|
-
|
34
|
-
var
|
35
|
-
|
44
|
+
//
|
45
|
+
function redirect_to_oauth(response, target_endpoint){
|
46
|
+
var _redirect_uri = fidor_config.app_url+"/oauth?ep="+target_endpoint
|
47
|
+
var redirect_uri = encodeURIComponent(_redirect_uri)
|
48
|
+
var oauth_url = fidor_config.fidor_oauth_url+
|
49
|
+
"/authorize?client_id="+fidor_config.client_id+
|
36
50
|
"&state=123&response_type=code&"+
|
37
51
|
"redirect_uri="+redirect_uri
|
38
52
|
response.writeHead(307, {"location" : oauth_url})
|
@@ -40,30 +54,45 @@ function redirect_to_oauth(response){
|
|
40
54
|
return
|
41
55
|
}
|
42
56
|
|
57
|
+
//
|
43
58
|
// Execute a POST request against the OAUTH token endpoint
|
44
59
|
// in order to exchange: code, client_id, client_secret,
|
45
|
-
//
|
46
|
-
|
47
|
-
|
60
|
+
// redirect_uri and grant_type for an auth_token.
|
61
|
+
//
|
62
|
+
// This corresponds to OAuth 3.2 Token Endpoint / 4.1.3 Access Token
|
63
|
+
// Request.
|
64
|
+
//
|
65
|
+
// Parameter:
|
66
|
+
// - the code that was returned from the Authorization Endpoint
|
67
|
+
// - the target endpoint (transactions/ or accounts/) that was requested
|
68
|
+
// in order to reconstruct the 'redirect-uri' parameter of the
|
69
|
+
// Authorization call.
|
70
|
+
// - callback(error, access_token)
|
71
|
+
//
|
72
|
+
function retrieve_access_token_from_code( code, target_endpoint, cb ) {
|
73
|
+
var oauth_url = url.parse(fidor_config.fidor_oauth_url)
|
74
|
+
|
48
75
|
// where to send the data ...
|
49
76
|
var postOptions = {
|
50
77
|
method: "POST",
|
51
|
-
path : oauth_url.path+"/
|
78
|
+
path : oauth_url.path+"/token",
|
52
79
|
port : oauth_url.port,
|
53
80
|
host : oauth_url.hostname
|
54
81
|
}
|
55
82
|
|
56
83
|
// ... what to send
|
84
|
+
var redirect_uri = fidor_config.app_url+"/oauth?ep="+target_endpoint
|
57
85
|
var postData = {
|
58
86
|
code : code,
|
59
87
|
client_id : fidor_config.client_id,
|
60
88
|
client_secret : fidor_config.client_secret,
|
61
|
-
redirect_uri : encodeURIComponent(
|
89
|
+
redirect_uri : encodeURIComponent(redirect_uri),
|
62
90
|
grant_type : "authorization_code"
|
63
91
|
}
|
64
92
|
postData = querystring.stringify(postData)
|
65
93
|
|
66
94
|
var http_module = oauth_url.protocol == "https:" ? https : http
|
95
|
+
|
67
96
|
var token_request = http_module.request(postOptions, function (res) {
|
68
97
|
// collect the data chunks we received and reassemble them
|
69
98
|
// on request end ...
|
@@ -74,7 +103,6 @@ function retrieve_access_token_from_code( code, cb ) {
|
|
74
103
|
|
75
104
|
res.on('end', function() {
|
76
105
|
var oauth_response = JSON.parse(data)
|
77
|
-
console.log(oauth_response)
|
78
106
|
cb(oauth_response.error, oauth_response.access_token)
|
79
107
|
})
|
80
108
|
})
|
@@ -87,39 +115,217 @@ function retrieve_access_token_from_code( code, cb ) {
|
|
87
115
|
token_request.end()
|
88
116
|
}
|
89
117
|
|
118
|
+
/************************************************************************
|
119
|
+
/* END: OAuth Calls
|
120
|
+
************************************************************************/
|
121
|
+
|
122
|
+
|
123
|
+
/************************************************************************
|
124
|
+
/* BEGIN: Cookie & Session Handling
|
125
|
+
************************************************************************/
|
126
|
+
var COOKIE_NAME="NODE_SESSION"
|
127
|
+
var sessions = {}
|
128
|
+
|
129
|
+
// retrieve the random session_id from the cookie.
|
130
|
+
function getSession(req) {
|
131
|
+
var cookies = req.headers.cookie
|
132
|
+
var session = null
|
133
|
+
if (cookies) {
|
134
|
+
var cookieArr = cookies.split(";")
|
135
|
+
for (var i = 0 ; i != cookieArr.length ; ++i) {
|
136
|
+
var keyValue = cookieArr[i].split("=")
|
137
|
+
if (keyValue && keyValue.length == 2 && keyValue[0].trim() == COOKIE_NAME) {
|
138
|
+
session = keyValue[1]
|
139
|
+
break
|
140
|
+
}
|
141
|
+
}
|
142
|
+
}
|
143
|
+
return session
|
144
|
+
}
|
145
|
+
function getAccessTokenFromSession(req) {
|
146
|
+
var session = getSession(req)
|
147
|
+
var access_token = null
|
148
|
+
if (session) {
|
149
|
+
access_token = sessions[session]
|
150
|
+
}
|
151
|
+
return access_token
|
152
|
+
}
|
153
|
+
function createSession(resp, access_token) {
|
154
|
+
function randomString(len) {
|
155
|
+
var hex = "0123456789abcdef"
|
156
|
+
var rnd = ""
|
157
|
+
for (var i = 0; i!= len; ++i) {
|
158
|
+
rnd += hex[Math.floor(Math.random()*hex.length)]
|
159
|
+
}
|
160
|
+
return rnd
|
161
|
+
}
|
162
|
+
var rnd = randomString(20)
|
163
|
+
sessions[rnd] = access_token
|
164
|
+
resp.setHeader("Set-Cookie", COOKIE_NAME+"="+rnd)
|
165
|
+
}
|
166
|
+
function removeSession(req, resp) {
|
167
|
+
// find cookie
|
168
|
+
var session = getSession(req)
|
169
|
+
// delete from sessions
|
170
|
+
delete sessions[session]
|
171
|
+
// set expired
|
172
|
+
resp.setHeader("Set-Cookie", COOKIE_NAME+"=nothing; expires=Thu, 01 Jan 1970 00:00:00 GMT")
|
173
|
+
}
|
174
|
+
|
175
|
+
/************************************************************************
|
176
|
+
/* END: Cookie & Session Handling
|
177
|
+
************************************************************************/
|
178
|
+
|
179
|
+
/************************************************************************
|
180
|
+
/* BEGIN: HTTP Handling
|
181
|
+
************************************************************************/
|
90
182
|
|
183
|
+
//
|
91
184
|
// Display a friendly message and links to the API Endpoints.
|
92
|
-
|
185
|
+
//
|
186
|
+
function renderWelcome(request, response) {
|
93
187
|
response.writeHead(200, {"Content-Type" : "text/html"})
|
94
|
-
|
95
|
-
console.log(content)
|
96
|
-
console.log(token)
|
97
|
-
content = content.replace(/{api_uri}/g, fidor_config.fidor_api_url)
|
98
|
-
response.end(content)
|
188
|
+
response.end(hello_template)
|
99
189
|
}
|
100
190
|
|
101
|
-
// main http functionality
|
102
|
-
function listener (request, response) {
|
103
191
|
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
192
|
+
|
193
|
+
|
194
|
+
function render (endpoint, req, res) {
|
195
|
+
//
|
196
|
+
// call the api endpoint and pipe the response from the API back to
|
197
|
+
// the caller
|
198
|
+
//
|
199
|
+
function pipeApi(endpoint, access_token, res) {
|
200
|
+
var api_endpoint = url.parse(fidor_config.fidor_api_url+endpoint)
|
201
|
+
var http_module = api_endpoint.protocol == "https:" ? https : http
|
202
|
+
var http_options = {
|
203
|
+
hostname: api_endpoint.hostname,
|
204
|
+
path: api_endpoint.path,
|
205
|
+
port: api_endpoint.port,
|
206
|
+
method: "GET",
|
207
|
+
headers: {
|
208
|
+
"Authorization": "Bearer "+access_token
|
209
|
+
}
|
210
|
+
}
|
211
|
+
|
212
|
+
var api_request = http_module.request(http_options, function(api_response) {
|
213
|
+
res.setHeader('Content-Type', api_response.headers['content-type'])
|
214
|
+
if (api_response.statusCode == 401) { // access_token has expired.
|
215
|
+
handleLogout(req, res, endpoint)
|
216
|
+
return
|
217
|
+
}
|
218
|
+
res.writeHead(api_response.statusCode, api_response.statusMessage)
|
219
|
+
api_response.on('data', function(chunk) {
|
220
|
+
res.write(chunk)
|
221
|
+
})
|
222
|
+
api_response.on('end', function(){
|
223
|
+
res.end()
|
224
|
+
})
|
225
|
+
})
|
226
|
+
|
227
|
+
api_request.on('error', function (err) {
|
228
|
+
res.writeHead(500, {'Content-Type': 'text/plain'})
|
229
|
+
res.end(err.toString())
|
230
|
+
})
|
231
|
+
api_request.end()
|
232
|
+
}
|
233
|
+
|
234
|
+
//
|
235
|
+
// utility to check whether access token is via session cookie, if not
|
236
|
+
// redirects account holder to OAuth Authorization Endpoint.
|
237
|
+
//
|
238
|
+
function getAccessToken(redirect, req, res, cb) {
|
239
|
+
var accesstoken = getAccessTokenFromSession(req)
|
240
|
+
if (!accesstoken) {
|
241
|
+
// start OAuth
|
242
|
+
redirect_to_oauth(res, redirect)
|
243
|
+
} else {
|
244
|
+
cb(null, accesstoken)
|
245
|
+
}
|
246
|
+
|
110
247
|
}
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
248
|
+
|
249
|
+
getAccessToken(endpoint, req, res, function (err, accesstoken) {
|
250
|
+
if (err) {
|
251
|
+
res.writeHead(500, {'Content-Type': 'text/plain'})
|
252
|
+
res.end(err.toString())
|
253
|
+
return
|
254
|
+
}
|
255
|
+
pipeApi(endpoint, accesstoken, res)
|
256
|
+
})
|
257
|
+
}
|
258
|
+
|
259
|
+
function renderTransactions (req, res){
|
260
|
+
render("/transactions", req, res)
|
261
|
+
}
|
262
|
+
function renderAccounts (req, res){
|
263
|
+
render("/accounts", req, res)
|
264
|
+
}
|
265
|
+
|
266
|
+
//
|
267
|
+
// retrieve the 'code' parameter from the redirect url the
|
268
|
+
// OAuth Authorization returns to the user's browser
|
269
|
+
//
|
270
|
+
function handleOAuthCallback(req, res) {
|
271
|
+
var u = url.parse(req.url)
|
272
|
+
var query = querystring.parse(u.query)
|
273
|
+
var code = query["code"]
|
274
|
+
var target = query["ep"]
|
275
|
+
|
276
|
+
if (code && target) {
|
277
|
+
retrieve_access_token_from_code( code, target, function (err, token) {
|
278
|
+
if (err) {
|
279
|
+
res.writeHead(500, {'Content-Type': 'text/plain'})
|
280
|
+
res.end(err.toString())
|
281
|
+
return
|
282
|
+
}
|
283
|
+
createSession(res, token)
|
284
|
+
res.writeHead(307, {"location" : target})
|
285
|
+
res.end()
|
116
286
|
})
|
117
287
|
} else {
|
118
|
-
|
119
|
-
|
120
|
-
|
288
|
+
res.writeHead(500, {'Content-Type': 'text/plain'})
|
289
|
+
res.end("missing code or target")
|
290
|
+
}
|
291
|
+
}
|
292
|
+
|
293
|
+
function handleLogout(req, res, endpoint) {
|
294
|
+
// clear session locally and in browser
|
295
|
+
removeSession(req, res)
|
296
|
+
res.writeHead(307, {"location" : endpoint})
|
297
|
+
res.end()
|
298
|
+
}
|
299
|
+
|
300
|
+
function listener (request, response) {
|
301
|
+
var u = url.parse(request.url)
|
302
|
+
|
303
|
+
if (request.method !== "GET") {
|
304
|
+
response.writeHead(403, "Forbidden")
|
305
|
+
response.end()
|
121
306
|
return
|
122
307
|
}
|
308
|
+
|
309
|
+
switch(u.pathname) {
|
310
|
+
case "/":
|
311
|
+
renderWelcome(request, response)
|
312
|
+
break
|
313
|
+
case "/transactions":
|
314
|
+
renderTransactions(request, response)
|
315
|
+
break
|
316
|
+
case "/accounts":
|
317
|
+
renderAccounts(request, response)
|
318
|
+
break
|
319
|
+
case "/oauth":
|
320
|
+
handleOAuthCallback(request, response)
|
321
|
+
break
|
322
|
+
case "/logout":
|
323
|
+
handleLogout(request, response, "/")
|
324
|
+
break
|
325
|
+
default:
|
326
|
+
response.writeHead(404, "Not Found")
|
327
|
+
}
|
328
|
+
|
123
329
|
}
|
124
330
|
|
125
331
|
// Execution starts here...
|
@@ -127,7 +333,7 @@ function listener (request, response) {
|
|
127
333
|
var url = require("url")
|
128
334
|
var querystring = require("querystring")
|
129
335
|
var http = require("http")
|
130
|
-
var https = require("
|
336
|
+
var https = require("https")
|
131
337
|
|
132
338
|
var _url = url.parse(fidor_config.app_url)
|
133
339
|
fidor_config.app_port = _url.port
|
@@ -145,8 +351,8 @@ var hello_template = ""+
|
|
145
351
|
"</head>"+
|
146
352
|
"<body>"+
|
147
353
|
" <h1>Welcome!</h1>"+
|
148
|
-
" <
|
149
|
-
" <p><a href='
|
150
|
-
" <p><a href='
|
354
|
+
" <p><a href='/transactions'>Transactions</a></p>"+
|
355
|
+
" <p><a href='/accounts'>Accounts</a></p>"+
|
356
|
+
" <p><a href='/logout'>Log Out</a></p>"+
|
151
357
|
"</body>"+
|
152
358
|
"</html>"
|
@@ -1,7 +1,7 @@
|
|
1
1
|
{
|
2
|
-
"display_name" : "PHP Plain",
|
2
|
+
"display_name" : "PHP oAuth Plain",
|
3
3
|
"description" : "A simple php script, showing how to get the access token",
|
4
|
-
"app_name":"
|
4
|
+
"app_name":"php_oauth_plain",
|
5
5
|
"app_url":"http://localhost:8000/example.php",
|
6
6
|
"callback_urls":"http://localhost:8000/example.php"
|
7
7
|
}
|
@@ -1,12 +1,13 @@
|
|
1
1
|
<?php
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
3
|
+
$app_url = "<APP_URL>"; # default http://localhost:8000/example.php
|
4
|
+
$app_id = "<CLIENT_ID>";
|
5
|
+
$app_secret = "<CLIENT_SECRET>";
|
6
|
+
$fidor_oauth_url= "<FIDOR_OAUTH_URL>"; # e.g Sandbox: https://aps.fidor.de/oauth / Live: https://apm.fidor.de/oauth
|
7
|
+
$fidor_api_url = "<FIDOR_API_URL>"; # e.g Sandbox: https://aps.fidor.de / Live: https://api.fidor.de
|
8
8
|
|
9
|
-
|
9
|
+
|
10
|
+
$code = $_REQUEST["code"];
|
10
11
|
|
11
12
|
# 1. redirect to authorize url
|
12
13
|
if(empty($code)) {
|
@@ -38,15 +39,13 @@
|
|
38
39
|
$context = stream_context_create($options);
|
39
40
|
$resp = json_decode(file_get_contents($token_url, false, $context));
|
40
41
|
|
41
|
-
|
42
|
-
$usr_url = $fidor_api_url . "/users/current?access_token=" . $resp->access_token;
|
43
|
-
$user = json_decode(file_get_contents($usr_url));
|
44
|
-
$transactions_url = $fidor_api_url . "/transactions?access_token=" . $resp->access_token;
|
45
|
-
echo( "<h2>Hello " . $user->email . "</h2>
|
42
|
+
echo( "<h2>Hello</h2>
|
46
43
|
<i>May I present the access token response:</i>
|
47
44
|
<blockquote>");
|
48
45
|
print_r($resp);
|
49
46
|
echo("</blockquote>
|
50
|
-
<p>Now use the access token
|
47
|
+
<p>Now use the access token in the request header in your favorite PHP HTTP method or via CURL: </p>
|
48
|
+
<blockquote>curl -v -H \"Authorization: Bearer ".$resp->access_token."\" ".$fidor_api_url."/transactions
|
49
|
+
</blockquote>");
|
51
50
|
|
52
|
-
?>
|
51
|
+
?>
|
@@ -0,0 +1,7 @@
|
|
1
|
+
{
|
2
|
+
"display_name" : "Ruby oAuth Plain",
|
3
|
+
"description" : "A simple Ruby app showing the oAuth dance to get and use the access token. Uses Sinatra as server.",
|
4
|
+
"app_name":"ruby_oauth_plain",
|
5
|
+
"app_url":"http://localhost:4567",
|
6
|
+
"callback_urls":"http://localhost:4567"
|
7
|
+
}
|
@@ -1,13 +1,13 @@
|
|
1
1
|
# Ruby Plain oAuth Login - Example
|
2
2
|
|
3
3
|
A single view that demonstrates the Fidor API OAuth login flow and how to get
|
4
|
-
an access token.
|
4
|
+
an access token. Uses Sinatra on its server side.
|
5
5
|
|
6
6
|
## Usage
|
7
7
|
|
8
8
|
This uses bundler to install the required gems:
|
9
9
|
|
10
|
-
cd
|
10
|
+
cd ruby_oauth_plain
|
11
11
|
bundle install
|
12
12
|
ruby example.rb
|
13
13
|
|
@@ -0,0 +1,39 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'sinatra'
|
3
|
+
require 'httparty'
|
4
|
+
|
5
|
+
get '/' do
|
6
|
+
# settings
|
7
|
+
@app_url = '<APP_URL>' # default for local installs: http://localhost:4567
|
8
|
+
@client_id = '<CLIENT_ID>'
|
9
|
+
@client_secret = '<CLIENT_SECRET>'
|
10
|
+
@fidor_oauth_url = '<FIDOR_OAUTH_URL>' # e.g Sandbox: https://aps.fidor.de/oauth / Live: https://apm.fidor.de/oauth
|
11
|
+
@fidor_api_url = '<FIDOR_API_URL>' # e.g Sandbox: https://aps.fidor.de / Live: https://api.fidor.de
|
12
|
+
|
13
|
+
# 1. redirect to authorize url
|
14
|
+
unless code = params["code"]
|
15
|
+
dialog_url = "#{@fidor_oauth_url}/authorize?client_id=#{@client_id}&redirect_uri=#{CGI::escape(@app_url)}&state=1234&response_type=code"
|
16
|
+
redirect dialog_url
|
17
|
+
end
|
18
|
+
|
19
|
+
# 2. get the access token, with code returned from auth dialog above
|
20
|
+
token_url = URI("#{@fidor_oauth_url}/token")
|
21
|
+
post_params = { client_id: @client_id,
|
22
|
+
redirect_uri: CGI::escape(@app_url),
|
23
|
+
code: code,
|
24
|
+
client_secret: @client_secret,
|
25
|
+
grant_type: 'authorization_code' }
|
26
|
+
resp = HTTParty.post(token_url, body: post_params )
|
27
|
+
|
28
|
+
# GET current user setting the access-token in the request header
|
29
|
+
user = HTTParty.get( "#{@fidor_api_url}/users/current",
|
30
|
+
headers: { 'Authorization' => "Bearer #{resp['access_token']}"} )
|
31
|
+
|
32
|
+
"<h2>Hello #{user['email']}</h2>
|
33
|
+
<i>May i present the access token response:</i>
|
34
|
+
<blockquote>#{resp.body}</blockquote>
|
35
|
+
<p>Now use the access token in the Header of your Requests, e.g. using CURL</p>
|
36
|
+
<blockquote>
|
37
|
+
curl -v -H \"Authorization: Bearer #{resp['access_token']}\" #{@fidor_api_url}/accounts
|
38
|
+
</blockquote>"
|
39
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: fidor_starter_kits
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.3.
|
4
|
+
version: 0.3.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Georg Leciejewski
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-06-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rubyzip
|
@@ -109,13 +109,13 @@ files:
|
|
109
109
|
- starter_kits/java_servlet/src/de/fidor/api/example/Example.java
|
110
110
|
- starter_kits/node_tx/.fidor_meta.json
|
111
111
|
- starter_kits/node_tx/example.js
|
112
|
-
- starter_kits/
|
113
|
-
- starter_kits/
|
114
|
-
- starter_kits/
|
115
|
-
- starter_kits/
|
116
|
-
- starter_kits/
|
117
|
-
- starter_kits/
|
118
|
-
- starter_kits/
|
112
|
+
- starter_kits/php_oauth_plain/.fidor_meta.json
|
113
|
+
- starter_kits/php_oauth_plain/README.md
|
114
|
+
- starter_kits/php_oauth_plain/example.php
|
115
|
+
- starter_kits/ruby_oauth_plain/.fidor_meta.json
|
116
|
+
- starter_kits/ruby_oauth_plain/Gemfile
|
117
|
+
- starter_kits/ruby_oauth_plain/README.md
|
118
|
+
- starter_kits/ruby_oauth_plain/example.rb
|
119
119
|
homepage: ''
|
120
120
|
licenses:
|
121
121
|
- MIT
|
@@ -1,40 +0,0 @@
|
|
1
|
-
require 'rubygems'
|
2
|
-
require 'sinatra'
|
3
|
-
require 'active_support/json'
|
4
|
-
require 'net/http'
|
5
|
-
|
6
|
-
get '/' do
|
7
|
-
# settings
|
8
|
-
@app_url = '<APP_URL>' # default for local installs: http://localhost:4567
|
9
|
-
@client_id = '<CLIENT_ID>'
|
10
|
-
@client_secret = '<CLIENT_SECRET>'
|
11
|
-
@fidor_oauth_url = '<FIDOR_OAUTH_URL>' # e.g https://fidor.com/oauth
|
12
|
-
@fidor_api_url = '<FIDOR_API_URL>' # e.g https://fidor.com/api_sandbox, https://fidor.com/api
|
13
|
-
|
14
|
-
# 1. redirect to authorize url
|
15
|
-
unless code = params["code"]
|
16
|
-
dialog_url = "#{@fidor_oauth_url}/authorize?client_id=#{@client_id}&redirect_uri=#{CGI::escape(@app_url)}&state=1234&response_type=code"
|
17
|
-
redirect dialog_url
|
18
|
-
end
|
19
|
-
|
20
|
-
# 2. get the access token, with code returned from auth dialog above
|
21
|
-
token_url = URI("#{@fidor_oauth_url}/token")
|
22
|
-
# GET and parse access_token response json
|
23
|
-
res = Net::HTTP.post_form(token_url, 'client_id' => @client_id,
|
24
|
-
'redirect_uri' => CGI::escape(@app_url),
|
25
|
-
'code' =>code,
|
26
|
-
'client_secret'=>@client_secret,
|
27
|
-
'grant_type'=>'authorization_code')
|
28
|
-
|
29
|
-
resp = ActiveSupport::JSON.decode(res.body)
|
30
|
-
|
31
|
-
# GET current user
|
32
|
-
usr_url = "#{@fidor_api_url}/users/current?access_token=#{resp['access_token']}"
|
33
|
-
user = ActiveSupport::JSON.decode( Net::HTTP.get URI(usr_url) )
|
34
|
-
account_url = "#{@fidor_api_url}/accounts?access_token=#{resp['access_token']}"
|
35
|
-
"<h2>Hello #{user['email']}</h2>
|
36
|
-
<i>May i present the access token response:</i>
|
37
|
-
<blockquote>#{resp.inspect}</blockquote>
|
38
|
-
<p>Now use the access token in <br> <a href='#{account_url}'>#{account_url}</a></p>
|
39
|
-
"
|
40
|
-
end
|