@internetarchive/ia-book-actions 0.0.5-4-03 → 0.0.5-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.
- package/demo/error.html +4 -0
- package/demo/index.html +13 -3
- package/package.json +2 -1
- package/src/components/show-dialog.js +115 -0
- package/src/core/services/actions-handler/actions-handler-service.js +78 -2
- package/src/core/services/archive-token-poller.js +88 -0
- package/src/ia-book-actions.js +28 -1
package/demo/error.html
ADDED
package/demo/index.html
CHANGED
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
body {
|
|
13
13
|
margin: 0;
|
|
14
14
|
text-align: center;
|
|
15
|
-
font-family: "Helvetica Neue",
|
|
15
|
+
font-family: "Helvetica Neue", Arial, Verdana, sans-serif;
|
|
16
16
|
}
|
|
17
17
|
#demo {
|
|
18
18
|
height: 50px;
|
|
@@ -71,10 +71,21 @@
|
|
|
71
71
|
float: left;
|
|
72
72
|
margin: 2px;
|
|
73
73
|
}
|
|
74
|
+
|
|
75
|
+
.ui-overlay {
|
|
76
|
+
position: fixed;
|
|
77
|
+
top: 0;
|
|
78
|
+
left: 0;
|
|
79
|
+
width: 100%;
|
|
80
|
+
height: 100%;
|
|
81
|
+
background: black;
|
|
82
|
+
opacity: 0.3;
|
|
83
|
+
}
|
|
74
84
|
</style>
|
|
75
85
|
</head>
|
|
76
86
|
|
|
77
87
|
<body>
|
|
88
|
+
|
|
78
89
|
<ia-book-actions></ia-book-actions>
|
|
79
90
|
|
|
80
91
|
<script type="module">
|
|
@@ -96,7 +107,7 @@
|
|
|
96
107
|
iaBookActions.userid = '';
|
|
97
108
|
iaBookActions.identifier = identifier;
|
|
98
109
|
iaBookActions.bookTitle = 'Contemporary Black biography. Volume 39 : profiles from the interContemporary Black biography. Volume 39';
|
|
99
|
-
iaBookActions.lendingStatus =
|
|
110
|
+
iaBookActions.lendingStatus = canBrowseAndBorrow;
|
|
100
111
|
iaBookActions.bwbPurchaseUrl = '';
|
|
101
112
|
iaBookActions.barType = '';
|
|
102
113
|
|
|
@@ -203,7 +214,6 @@
|
|
|
203
214
|
})
|
|
204
215
|
});
|
|
205
216
|
</script>
|
|
206
|
-
|
|
207
217
|
<div>
|
|
208
218
|
<fieldset>
|
|
209
219
|
<legend>Dev testing for book title bar</legend>
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@internetarchive/ia-book-actions",
|
|
3
|
-
"version": "0.0.5-
|
|
3
|
+
"version": "0.0.5-5",
|
|
4
4
|
"description": "Bookreader actions for borrowable book",
|
|
5
5
|
"author": "Internet Archive",
|
|
6
6
|
"license": "AGPL-3.0-only",
|
|
@@ -21,6 +21,7 @@
|
|
|
21
21
|
"@internetarchive/ia-icons": "^1.2.2",
|
|
22
22
|
"@internetarchive/icon-bookmark": "^1.1.3",
|
|
23
23
|
"@internetarchive/icon-info": "^1.2.6",
|
|
24
|
+
"@internetarchive/icon-close": "^1.1.3",
|
|
24
25
|
"@internetarchive/shared-resize-observer": "^0.0.1",
|
|
25
26
|
"lit-element": "^2.4.0",
|
|
26
27
|
"lit-html": "^1.3.0"
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
/* eslint-disable */
|
|
2
|
+
import { LitElement, html, css } from 'lit-element';
|
|
3
|
+
import { classMap } from 'lit-html/directives/class-map';
|
|
4
|
+
|
|
5
|
+
import '@internetarchive/icon-close/icon-close.js';
|
|
6
|
+
import buttonBaseStyle from '../assets/styles/ia-button.js';
|
|
7
|
+
|
|
8
|
+
export class showDialog extends LitElement {
|
|
9
|
+
static get properties() {
|
|
10
|
+
return {
|
|
11
|
+
opened: { type: Boolean },
|
|
12
|
+
title: { type: Boolean },
|
|
13
|
+
body: { type: Boolean },
|
|
14
|
+
actions: { type: Array },
|
|
15
|
+
};
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
constructor() {
|
|
19
|
+
super();
|
|
20
|
+
this.opened = false;
|
|
21
|
+
this.title = 'Error';
|
|
22
|
+
this.body =
|
|
23
|
+
'Unexpected error: loan does not exist. Please try deleting your archive.org cookie.';
|
|
24
|
+
this.actions = [];
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
render() {
|
|
28
|
+
return html`
|
|
29
|
+
<div
|
|
30
|
+
class="${classMap({
|
|
31
|
+
dialog: true,
|
|
32
|
+
opened: this.opened,
|
|
33
|
+
closed: !this.opened,
|
|
34
|
+
})}"
|
|
35
|
+
>
|
|
36
|
+
<div class="dialog-head">
|
|
37
|
+
${this.title}
|
|
38
|
+
<span
|
|
39
|
+
@click="${() =>
|
|
40
|
+
this.dispatchEvent(new CustomEvent('dialog.close'))}"
|
|
41
|
+
>
|
|
42
|
+
<ia-icon-close fill-color="blue"></ia-icon-close
|
|
43
|
+
></span>
|
|
44
|
+
</div>
|
|
45
|
+
<div class="dialog-body">${this.body}</div>
|
|
46
|
+
<div class="dialog-foot">${this.renderActionButton()}</div>
|
|
47
|
+
</div>
|
|
48
|
+
`;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
renderActionButton() {
|
|
52
|
+
return this.actions.map(
|
|
53
|
+
action =>
|
|
54
|
+
html`<button class=${action.className} @click=${action.callback}>
|
|
55
|
+
${action.text}
|
|
56
|
+
</button>`
|
|
57
|
+
);
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
static get styles() {
|
|
61
|
+
const dialogStyle = css`
|
|
62
|
+
:host {
|
|
63
|
+
color: #343434;
|
|
64
|
+
font-size: 1.6rem;
|
|
65
|
+
}
|
|
66
|
+
.dialog {
|
|
67
|
+
position: absolute;
|
|
68
|
+
background: #fff;
|
|
69
|
+
border-radius: 1.2rem;
|
|
70
|
+
z-index: 3000;
|
|
71
|
+
flex-direction: column;
|
|
72
|
+
width: 400px;
|
|
73
|
+
max-width: 500px;
|
|
74
|
+
left: 50%;
|
|
75
|
+
transform: translateX(-50%);
|
|
76
|
+
|
|
77
|
+
border: 2px solid #ccc;
|
|
78
|
+
border-radius: 12px;
|
|
79
|
+
box-shadow: 0px 0px 27px 6px rgb(66 66 66 / 80%);
|
|
80
|
+
}
|
|
81
|
+
.dialog-head,
|
|
82
|
+
.dialog-body,
|
|
83
|
+
.dialog-foot {
|
|
84
|
+
padding: 1rem;
|
|
85
|
+
user-select: none;
|
|
86
|
+
text-align: left;
|
|
87
|
+
}
|
|
88
|
+
.dialog-body {
|
|
89
|
+
border: 1px solid #d8d8d8;
|
|
90
|
+
}
|
|
91
|
+
ia-icon-close {
|
|
92
|
+
float: right;
|
|
93
|
+
display: inline-block;
|
|
94
|
+
width: 2.5rem;
|
|
95
|
+
height: 2.5rem;
|
|
96
|
+
vertical-align: middle;
|
|
97
|
+
--iconFillColor: #333;
|
|
98
|
+
cursor: pointer;
|
|
99
|
+
}
|
|
100
|
+
.opened {
|
|
101
|
+
display: flex;
|
|
102
|
+
}
|
|
103
|
+
.closed {
|
|
104
|
+
display: none;
|
|
105
|
+
}
|
|
106
|
+
a {
|
|
107
|
+
text-decoration: none;
|
|
108
|
+
}
|
|
109
|
+
`;
|
|
110
|
+
|
|
111
|
+
return [buttonBaseStyle, dialogStyle];
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
customElements.define('show-dialog', showDialog);
|
|
@@ -11,6 +11,7 @@ export default function ActionsHandlerService(options) {
|
|
|
11
11
|
data: {},
|
|
12
12
|
success() {},
|
|
13
13
|
error: null,
|
|
14
|
+
callback() {},
|
|
14
15
|
loader: true,
|
|
15
16
|
type: 'POST',
|
|
16
17
|
...options,
|
|
@@ -22,7 +23,7 @@ export default function ActionsHandlerService(options) {
|
|
|
22
23
|
|
|
23
24
|
let baseHost = '';
|
|
24
25
|
if (window.location.pathname === '/demo/') {
|
|
25
|
-
baseHost = `/demo/`;
|
|
26
|
+
baseHost = `/demo/`; // http://localhost:8000/demo/error.html
|
|
26
27
|
} else {
|
|
27
28
|
baseHost = `/services/loans/loan`;
|
|
28
29
|
}
|
|
@@ -36,15 +37,90 @@ export default function ActionsHandlerService(options) {
|
|
|
36
37
|
body: formData,
|
|
37
38
|
})
|
|
38
39
|
.then(response => {
|
|
40
|
+
console.log('response', response);
|
|
41
|
+
|
|
42
|
+
if (baseHost == '/demo/') {
|
|
43
|
+
// option.callback('{"result": true, "token": "token-response"}');
|
|
44
|
+
// option.callback('{"error": "Unexpected error. Please email this link to openlibrary@archive.org with the subject: Unexpected error. Thank you."}');
|
|
45
|
+
|
|
46
|
+
showDialog(
|
|
47
|
+
option.action,
|
|
48
|
+
'{"error": "Unexpected error. Please email this link to openlibrary@archive.org with the subject: Unexpected error. Thank you."}'
|
|
49
|
+
);
|
|
50
|
+
// showDialog('{"result": true, "token": "token-response"}');
|
|
51
|
+
}
|
|
52
|
+
// showDialog(option.action, response);
|
|
53
|
+
// option.callback(response);
|
|
54
|
+
|
|
39
55
|
if (response.status === 200) {
|
|
40
56
|
option.success.call();
|
|
41
57
|
}
|
|
42
58
|
})
|
|
43
59
|
.catch(error => {
|
|
44
|
-
console.log(error);
|
|
60
|
+
console.log('error', error);
|
|
61
|
+
// option.callback(error);
|
|
62
|
+
|
|
63
|
+
if (baseHost == '/demo/') {
|
|
64
|
+
showDialog(
|
|
65
|
+
option.action,
|
|
66
|
+
'{"error": "Unexpected error. Please email this link to openlibrary@archive.org with the subject: Unexpected error. Thank you."}'
|
|
67
|
+
);
|
|
68
|
+
// showDialog('{"result": true, "token": "token-response"}');
|
|
69
|
+
} else {
|
|
70
|
+
showDialog(option.action, error);
|
|
71
|
+
}
|
|
45
72
|
});
|
|
46
73
|
}
|
|
47
74
|
|
|
75
|
+
function showDialog(action, xhrResponse) {
|
|
76
|
+
const showDialog = document
|
|
77
|
+
.querySelector('ia-book-actions')
|
|
78
|
+
.shadowRoot.querySelector('show-dialog');
|
|
79
|
+
|
|
80
|
+
let title = 'Connection error';
|
|
81
|
+
let body = 'Please check internet connection.';
|
|
82
|
+
let actions = [
|
|
83
|
+
{
|
|
84
|
+
text: 'Okay',
|
|
85
|
+
callback: () => {
|
|
86
|
+
weAreBack();
|
|
87
|
+
this.updateToken();
|
|
88
|
+
},
|
|
89
|
+
className: 'ia-button primary',
|
|
90
|
+
},
|
|
91
|
+
];
|
|
92
|
+
|
|
93
|
+
// Specific error
|
|
94
|
+
const data = JSON.parse(xhrResponse);
|
|
95
|
+
console.log('data', data);
|
|
96
|
+
if (data.error) {
|
|
97
|
+
title = 'Sorry!';
|
|
98
|
+
body = data.error;
|
|
99
|
+
// Only go back to item button on error
|
|
100
|
+
actions = [
|
|
101
|
+
{
|
|
102
|
+
text: 'Back to item details',
|
|
103
|
+
callback: () => {
|
|
104
|
+
URLHelper.goToUrl(this.lendingStatus.bookUrl);
|
|
105
|
+
},
|
|
106
|
+
className: 'ia-button primary',
|
|
107
|
+
},
|
|
108
|
+
];
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
showDialog.opened = true;
|
|
112
|
+
showDialog.title = title;
|
|
113
|
+
showDialog.body = body;
|
|
114
|
+
if (action === 'create_token') {
|
|
115
|
+
showDialog.actions = actions;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
const overlayElement = document.createElement('div');
|
|
119
|
+
overlayElement.className = 'ui-overlay';
|
|
120
|
+
console.log(overlayElement);
|
|
121
|
+
document.getElementsByTagName('body')[0].appendChild(overlayElement);
|
|
122
|
+
}
|
|
123
|
+
|
|
48
124
|
function showActionButtonLoader() {
|
|
49
125
|
const collapsibleElement = document
|
|
50
126
|
.querySelector('ia-book-actions')
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
/* eslint-disable */
|
|
2
|
+
|
|
3
|
+
import ActionsHandlerService from './actions-handler/actions-handler-service.js';
|
|
4
|
+
import { URLHelper } from '../config/url-helper.js';
|
|
5
|
+
|
|
6
|
+
import '../../components/show-dialog.js';
|
|
7
|
+
|
|
8
|
+
export default class ArchiveOrgTokenPoller {
|
|
9
|
+
constructor(identifier, lendingStatus) {
|
|
10
|
+
this.identifier = identifier;
|
|
11
|
+
this.lendingStatus = lendingStatus;
|
|
12
|
+
this.pollingDelay = 6000; // 60000 ms = 1 min
|
|
13
|
+
this.tokenInterval = null;
|
|
14
|
+
this.showDialog = document
|
|
15
|
+
.querySelector('ia-book-actions')
|
|
16
|
+
.shadowRoot.querySelector('show-dialog');
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
init() {
|
|
20
|
+
console.log('ArchiveOrgTokenPoller started...');
|
|
21
|
+
// Do an initial token, then set an interval
|
|
22
|
+
this.tokenInterval = setInterval(() => {
|
|
23
|
+
this.updateToken();
|
|
24
|
+
}, this.pollingDelay);
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
updateToken() {
|
|
28
|
+
ActionsHandlerService({
|
|
29
|
+
identifier: this.identifier,
|
|
30
|
+
action: 'create_token',
|
|
31
|
+
// callback: (xhrResponse) => {
|
|
32
|
+
// console.log('xhrResponse', xhrResponse);
|
|
33
|
+
// if (xhrResponse.status === true) {
|
|
34
|
+
// this.hideErrorDialog(); // remove overlay and message box...
|
|
35
|
+
// // this.showErrorDialog(xhrResponse);
|
|
36
|
+
// } else {
|
|
37
|
+
// this.showErrorDialog(xhrResponse);
|
|
38
|
+
// }
|
|
39
|
+
// },
|
|
40
|
+
loader: false,
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
hideErrorDialog() {
|
|
45
|
+
this.showDialog.dialogVisible = false;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
showErrorDialog(xhrResponse) {
|
|
49
|
+
let title = 'Connection error';
|
|
50
|
+
let body = 'Please check internet connection.';
|
|
51
|
+
let actions = [
|
|
52
|
+
{
|
|
53
|
+
text: 'Okay',
|
|
54
|
+
callback: () => {
|
|
55
|
+
weAreBack();
|
|
56
|
+
this.updateToken();
|
|
57
|
+
},
|
|
58
|
+
className: 'ia-button primary',
|
|
59
|
+
},
|
|
60
|
+
];
|
|
61
|
+
|
|
62
|
+
// Specific error
|
|
63
|
+
const data = JSON.parse(xhrResponse);
|
|
64
|
+
if (data.error) {
|
|
65
|
+
title = 'Sorry!';
|
|
66
|
+
body = data.error;
|
|
67
|
+
// Only go back to item button on error
|
|
68
|
+
actions = [
|
|
69
|
+
{
|
|
70
|
+
text: 'Back to item details',
|
|
71
|
+
callback: () => {
|
|
72
|
+
URLHelper.goToUrl(this.lendingStatus.bookUrl);
|
|
73
|
+
},
|
|
74
|
+
className: 'ia-button primary',
|
|
75
|
+
},
|
|
76
|
+
];
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
const showDialog = document
|
|
80
|
+
.querySelector('ia-book-actions')
|
|
81
|
+
.shadowRoot.querySelector('show-dialog');
|
|
82
|
+
|
|
83
|
+
showDialog.opened = true;
|
|
84
|
+
showDialog.title = title;
|
|
85
|
+
showDialog.body = body;
|
|
86
|
+
showDialog.actions = actions;
|
|
87
|
+
}
|
|
88
|
+
}
|
package/src/ia-book-actions.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/* eslint-disable
|
|
1
|
+
/* eslint-disable */
|
|
2
2
|
import { html, css, LitElement } from 'lit-element';
|
|
3
3
|
|
|
4
4
|
import { SharedResizeObserver } from '@internetarchive/shared-resize-observer';
|
|
@@ -7,8 +7,11 @@ import './components/collapsible-action-group.js';
|
|
|
7
7
|
import './components/book-title-bar.js';
|
|
8
8
|
import './components/text-group.js';
|
|
9
9
|
import './components/info-icon.js';
|
|
10
|
+
import './components/show-dialog.js';
|
|
10
11
|
|
|
11
12
|
import GetLendingActions from './core/services/get-lending-actions.js';
|
|
13
|
+
import ArchiveOrgTokenPoller from './core/services/archive-token-poller.js';
|
|
14
|
+
|
|
12
15
|
import { mobileContainerWidth } from './core/config/constants.js';
|
|
13
16
|
|
|
14
17
|
export default class IABookActions extends LitElement {
|
|
@@ -22,6 +25,7 @@ export default class IABookActions extends LitElement {
|
|
|
22
25
|
bwbPurchaseUrl: { type: String },
|
|
23
26
|
barType: { type: String },
|
|
24
27
|
sharedObserver: { attribute: false },
|
|
28
|
+
dialogVisible: { type: Boolean },
|
|
25
29
|
};
|
|
26
30
|
}
|
|
27
31
|
|
|
@@ -40,6 +44,7 @@ export default class IABookActions extends LitElement {
|
|
|
40
44
|
this.primaryColor = 'primary';
|
|
41
45
|
this.secondaryActions = [];
|
|
42
46
|
this.lendingOptions = {};
|
|
47
|
+
this.dialogVisible = true;
|
|
43
48
|
}
|
|
44
49
|
|
|
45
50
|
disconnectedCallback() {
|
|
@@ -145,6 +150,14 @@ export default class IABookActions extends LitElement {
|
|
|
145
150
|
!this.lendingStatus.browseHasExpired
|
|
146
151
|
) {
|
|
147
152
|
this.startBrowseTimer();
|
|
153
|
+
|
|
154
|
+
// token poller start from here...
|
|
155
|
+
const tokenPoller = new ArchiveOrgTokenPoller(
|
|
156
|
+
this.identifier,
|
|
157
|
+
this.lendingStatus
|
|
158
|
+
);
|
|
159
|
+
tokenPoller.init();
|
|
160
|
+
return;
|
|
148
161
|
}
|
|
149
162
|
}
|
|
150
163
|
|
|
@@ -153,9 +166,23 @@ export default class IABookActions extends LitElement {
|
|
|
153
166
|
<section class="lending-wrapper">
|
|
154
167
|
${this.barType === 'title' ? this.bookTitleBar : this.bookActionBar}
|
|
155
168
|
</section>
|
|
169
|
+
|
|
170
|
+
<show-dialog
|
|
171
|
+
?opened="${this.dialogVisible}"
|
|
172
|
+
@dialog.close="${() => this.closeDialog(this)}"
|
|
173
|
+
></show-dialog>
|
|
156
174
|
`;
|
|
157
175
|
}
|
|
158
176
|
|
|
177
|
+
toggleDialog(e) {
|
|
178
|
+
this.dialogVisible = !this.dialogVisible;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
closeDialog(e) {
|
|
182
|
+
this.dialogVisible = false;
|
|
183
|
+
console.log('should close...', this.dialogVisible);
|
|
184
|
+
}
|
|
185
|
+
|
|
159
186
|
get bookTitleBar() {
|
|
160
187
|
return html`<book-title-bar
|
|
161
188
|
.identifier=${this.identifier}
|