@internetarchive/ia-book-actions 1.4.1 → 1.4.3-alpha-adminsticky

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.
@@ -11,16 +11,17 @@ jobs:
11
11
  runs-on: ubuntu-latest
12
12
 
13
13
  steps:
14
- - uses: actions/checkout@v4
15
- - uses: actions/setup-node@v3
14
+ - uses: actions/checkout@v4.1.1
15
+ - uses: actions/setup-node@v4.0.2
16
16
  with:
17
- node-version: 16.x
17
+ node-version: 20.x
18
18
 
19
19
  - name: Install dependencies
20
20
  run: yarn install
21
21
 
22
- # - name: Run tests
23
- # run: yarn run test
22
+ - name: Run tests
23
+ run: yarn run test
24
24
 
25
- # - name: Upload reports
26
- # run: npx codecov
25
+ - uses: codecov/codecov-action@v5
26
+ with:
27
+ token: ${{ secrets.CODECOV_TOKEN }}
@@ -12,26 +12,53 @@ on:
12
12
  - synchronize
13
13
  - closed
14
14
 
15
+ permissions:
16
+ contents: write
17
+ pull-requests: write
18
+
15
19
  concurrency: preview-${{ github.ref }}
16
20
 
21
+ env:
22
+ PREVIEW_BRANCH: gh-pages
17
23
  jobs:
18
24
  deploy-preview:
19
- runs-on: ubuntu-20.04
25
+ runs-on: ubuntu-latest
20
26
  steps:
21
27
  - name: Checkout
22
28
  uses: actions/checkout@v4
23
-
24
- - uses: actions/setup-node@v3
25
- with:
26
- node-version: 20.x
29
+ - uses: actions/setup-node@v4
27
30
 
28
31
  - name: Install and Build
29
32
  run: |
30
33
  yarn install
31
34
  yarn prepare:ghpages
35
+
32
36
  # Reference: https://github.com/rossjrw/pr-preview-action
33
37
  - name: Deploy preview
34
38
  uses: rossjrw/pr-preview-action@v1
39
+ id: preview-step
35
40
  with:
36
41
  source-dir: ./ghpages/
37
42
  umbrella-dir: pr
43
+ preview-branch: ${{ env.PREVIEW_BRANCH }}
44
+ comment: false
45
+
46
+ - uses: marocchino/sticky-pull-request-comment@v2
47
+ if: steps.preview-step.outputs.deployment-action == 'deploy'
48
+ with:
49
+ header: pr-preview
50
+ message: |
51
+ [PR Preview Action](https://github.com/rossjrw/pr-preview-action) ${{ steps.preview-step.outputs.action-version }}
52
+ :---:
53
+ | <p></p> :rocket: View preview at <br> ${{ steps.preview-step.outputs.preview-url }} <br><br>
54
+ | <h6>Built to branch [`${{ env.PREVIEW_BRANCH }}`](${{ github.server_url }}/${{ github.repository }}/tree/${{ env.PREVIEW_BRANCH }}) at ${{ steps.preview-step.outputs.action-start-time }}. <br> Preview will be ready when the [GitHub Pages deployment](${{ github.server_url }}/${{ github.repository }}/deployments) is complete. <br><br> </h6>
55
+
56
+ - uses: marocchino/sticky-pull-request-comment@v2
57
+ if: steps.preview-step.outputs.deployment-action == 'remove'
58
+ with:
59
+ header: pr-preview
60
+ message: |
61
+ [PR Preview Action](https://github.com/rossjrw/pr-preview-action) ${{ steps.preview-step.outputs.action-version }}
62
+ :---:
63
+ Preview removed because the pull request was closed.
64
+ ${{ steps.preview-step.outputs.action-start-time }}
package/README.md CHANGED
@@ -1,12 +1,21 @@
1
- # Component for lendable and embed items
2
1
 
3
- The book action button component build on LitElement with support for custom content and light DOM elements.
2
+ ![Build Status](https://github.com/internetarchive/iaux-book-actions/actions/workflows/ci.yml/badge.svg) [![codecov](https://codecov.io/gh/internetarchive/iaux-book-actions/branch/main/graph/badge.svg?token=ZOYRJ2BV9W)](https://codecov.io/gh/internetarchive/iaux-book-actions)
3
+
4
+ # Internet Archive Book Lending Actions
5
+
6
+ This WebComponent, built using the [IA Typescript WebComponent Template](https://github.com/internetarchive/iaux-typescript-wc-template), provides support for Bookreader actions for borrowable books on Internet Archive. It extends the [Open WebComponents generator](https://open-wc.org/docs/development/generator/) with Internet Archive-specific features and developer tools.
4
7
 
5
8
  ## Installation
6
9
  ```bash
7
10
  yarn install --save @internetarchive/ia-book-actions
8
11
  ```
9
12
 
13
+ ## Local Demo with `web-dev-server`
14
+ ```bash
15
+ yarn start
16
+ ```
17
+ To run a local development server that serves the basic demo located in `index.html`
18
+
10
19
  ## Usage of Book Actions
11
20
  ```html
12
21
  <!-- index.html -->
package/package.json CHANGED
@@ -1,9 +1,13 @@
1
1
  {
2
2
  "name": "@internetarchive/ia-book-actions",
3
- "version": "1.4.1",
4
3
  "description": "Bookreader actions for borrowable book",
4
+ "repository": {
5
+ "type": "git",
6
+ "url": "git+https://github.com/internetarchive/iaux-account-settings.git"
7
+ },
5
8
  "author": "Internet Archive",
6
9
  "license": "AGPL-3.0-only",
10
+ "version": "1.4.3-alpha-adminsticky",
7
11
  "main": "index.js",
8
12
  "module": "index.js",
9
13
  "publishConfig": {
@@ -15,28 +19,27 @@
15
19
  "prepare": "rimraf dist && husky install",
16
20
  "lint": "eslint --ext \"./src/*.js\",.html . --ignore-path .gitignore && prettier \"./src/*.js\" --check --ignore-path .gitignore",
17
21
  "format": "eslint --ext \"./src/*.js\",.html . --fix --ignore-path .gitignore && prettier \"./src/*.js\" --write --ignore-path .gitignore",
18
- "test": "yarn run lint && yarn test:fast",
19
- "test:fast": "web-test-runner --coverage --playwright --browsers chromium firefox webkit",
22
+ "test": "yarn run format && yarn run lint && yarn test:fast --coverage",
23
+ "test:fast": "web-test-runner",
20
24
  "test:watch": "web-test-runner --watch --playwright --browsers chromium firefox webkit",
21
25
  "deploy": "yarn run deploy:run -e $(git branch --show-current)",
22
26
  "deploy:run": "yarn run prepare:ghpages && touch ghpages/.nojekyll && yarn run deploy:gh",
23
27
  "deploy:gh": "gh-pages -t -d ghpages -m \"Build for $(git log --pretty=format:\"%h %an %ai %s\" -n1) [skip ci]\""
24
28
  },
25
29
  "dependencies": {
26
- "@internetarchive/icon-info": "1.3.5",
30
+ "@internetarchive/icon-info": "^1.4.1",
27
31
  "@internetarchive/local-cache": "^0.2.1",
28
- "@internetarchive/modal-manager": "2.0.0",
32
+ "@internetarchive/modal-manager": "^2.0.0",
29
33
  "@internetarchive/shared-resize-observer": "^0.2.0",
30
- "install-deps": "^1.1.0",
31
- "lit": "^2.8.0"
34
+ "lit": "^2.8.0 || ^3.3.2"
32
35
  },
33
36
  "devDependencies": {
34
37
  "@open-wc/eslint-config": "^4.2.0",
35
- "@open-wc/testing": "^2.0.0",
36
- "@web/dev-server": "^0.1.1",
37
- "@web/dev-server-esbuild": "^0.2.16",
38
- "@web/test-runner": "^0.11.7",
39
- "@web/test-runner-playwright": "^0.8.8",
38
+ "@open-wc/testing": "^4.0.0",
39
+ "@web/dev-server": "^0.4.6",
40
+ "@web/dev-server-esbuild": "^1.0.5",
41
+ "@web/test-runner": "^0.20.2",
42
+ "@web/test-runner-playwright": "^0.11.1",
40
43
  "eslint": "^7.32.0",
41
44
  "eslint-config-prettier": "^6.11.0",
42
45
  "eslint-plugin-import": "^2.22.1",
@@ -409,6 +409,7 @@ export default class ActionsHandler extends LitElement {
409
409
  */
410
410
  setStickyAdminAccess(value) {
411
411
  const domain = window.location.hostname === 'localhost' ? 'localhost' : '.archive.org';
412
- Cookies.setItem('sticky-admin-access', value, '', '/', domain);
412
+ const expires = new Date(Date.now() + 30 * 24 * 60 * 60 * 1000); // 30 days from now
413
+ Cookies.setItem('sticky-admin-access', value, expires, '/', domain);
413
414
  }
414
415
  }
@@ -120,7 +120,12 @@ export default class IABookActions extends LitElement {
120
120
  * @property {boolean} renewNow - key to determine if need to renew now
121
121
  * @property {number} secondsLeft - seconds left in active loan
122
122
  */
123
- this.loanRenewResult = { texts: '', renewNow: false, secondsLeft: 0, renewType: '' };
123
+ this.loanRenewResult = {
124
+ texts: '',
125
+ renewNow: false,
126
+ secondsLeft: 0,
127
+ renewType: '',
128
+ };
124
129
  }
125
130
 
126
131
  disconnectedCallback() {
@@ -535,11 +540,8 @@ export default class IABookActions extends LitElement {
535
540
  async startBrowseTimer() {
536
541
  window?.IALendingIntervals?.clearBrowseExpireTimeout();
537
542
 
538
- const {
539
- browsingExpired,
540
- user_has_browsed,
541
- secondsLeftOnLoan,
542
- } = this.lendingStatus;
543
+ const { browsingExpired, user_has_browsed, secondsLeftOnLoan } =
544
+ this.lendingStatus;
543
545
 
544
546
  if (!user_has_browsed || browsingExpired) {
545
547
  log('startBrowseTimer --- !user_has_browsed || browsingExpired', {
@@ -0,0 +1,91 @@
1
+ import { expect, fixture } from '@open-wc/testing';
2
+ import sinon from 'sinon';
3
+
4
+ import ActionsHandler from '../../../src/core/services/actions-handler/actions-handler.js';
5
+
6
+ // Define a temporary tag for this element for testing
7
+ const TEST_TAG = 'ia-actions-handler-test';
8
+ if (!customElements.get(TEST_TAG)) {
9
+ customElements.define(TEST_TAG, ActionsHandler);
10
+ }
11
+
12
+ describe('ActionsHandler#setStickyAdminAccess', () => {
13
+ let clock;
14
+ let lastSetCookie;
15
+ let cookieOverridden = false;
16
+ let actionsHandlerFixture;
17
+
18
+ beforeEach(async () => {
19
+ // Intercept document.cookie writes to capture the full cookie string
20
+ Object.defineProperty(document, 'cookie', {
21
+ configurable: true,
22
+ get() {
23
+ return '';
24
+ },
25
+ set(value) {
26
+ lastSetCookie = value;
27
+ },
28
+ });
29
+ cookieOverridden = true;
30
+
31
+ // Create the element via fixture (portable across browsers)
32
+ actionsHandlerFixture = await fixture(`<${TEST_TAG}></${TEST_TAG}>`);
33
+ });
34
+
35
+ afterEach(() => {
36
+ sinon.restore();
37
+ if (clock) {
38
+ clock.restore();
39
+ clock = undefined;
40
+ }
41
+ // restore document.cookie
42
+ if (cookieOverridden) {
43
+ try {
44
+ // remove our instance-level override
45
+ // eslint-disable-next-line no-param-reassign
46
+ delete document.cookie;
47
+ } catch (e) {
48
+ // ignore
49
+ }
50
+ cookieOverridden = false;
51
+ }
52
+ lastSetCookie = undefined;
53
+ });
54
+
55
+ it('sets the sticky-admin-access cookie with correct domain, path, and 30-day expiration', async () => {
56
+ // Arrange: fix time and stub cookie writer
57
+ const now = new Date('2025-01-01T00:00:00.000Z');
58
+ clock = sinon.useFakeTimers({ now: now.getTime() });
59
+
60
+ // Calculate expected values based on current environment
61
+ const expectedDomain = window.location.hostname === 'localhost' ? 'localhost' : '.archive.org';
62
+ const expectedExpires = new Date(now.getTime() + 30 * 24 * 60 * 60 * 1000);
63
+
64
+ // Act: call the method on the element created in beforeEach
65
+ actionsHandlerFixture.setStickyAdminAccess(true);
66
+
67
+ // Assert: verify the composed cookie string
68
+ expect(lastSetCookie).to.be.a('string');
69
+ // Name and value
70
+ expect(lastSetCookie).to.contain(`${encodeURIComponent('sticky-admin-access')}=${encodeURIComponent('true')}`);
71
+ // Domain
72
+ expect(lastSetCookie).to.contain(`domain=${expectedDomain}`);
73
+ // Path
74
+ expect(lastSetCookie).to.contain('path=/');
75
+ // Expiration close to 30 days from now
76
+ const match = /expires=([^;]+)/.exec(lastSetCookie);
77
+ expect(match).to.not.equal(null);
78
+ const expiresStr = match && match[1];
79
+ const parsed = expiresStr ? new Date(expiresStr) : null;
80
+ expect(parsed).to.be.instanceOf(Date);
81
+ expect(parsed && parsed.getTime()).to.equal(expectedExpires.getTime());
82
+ });
83
+
84
+ it('sets the cookie value to false when disabling', async () => {
85
+ // Act
86
+ actionsHandlerFixture.setStickyAdminAccess(false);
87
+
88
+ expect(lastSetCookie).to.be.a('string');
89
+ expect(lastSetCookie).to.contain(`${encodeURIComponent('sticky-admin-access')}=${encodeURIComponent('false')}`);
90
+ });
91
+ });
@@ -3,7 +3,7 @@
3
3
  export default /** @type {import("@web/test-runner").TestRunnerConfig} */ ({
4
4
  files: 'test/**/*.test.js',
5
5
  nodeResolve: true,
6
- watch: true,
6
+ watch: false,
7
7
 
8
8
  /** Compile JS for older browsers. Requires @web/dev-server-esbuild plugin */
9
9
  esbuildTarget: 'auto',