Code coverage of 90%, added browser isolation and possibility to set cache dir
parent
0773f77c2c
commit
f637c4759d
86
app/index.js
86
app/index.js
|
@ -2,7 +2,6 @@
|
||||||
|
|
||||||
// Core modules
|
// Core modules
|
||||||
const fs = require('fs');
|
const fs = require('fs');
|
||||||
const path = require('path');
|
|
||||||
|
|
||||||
// Public modules from npm
|
// Public modules from npm
|
||||||
const urlExist = require('url-exist');
|
const urlExist = require('url-exist');
|
||||||
|
@ -19,19 +18,15 @@ const {
|
||||||
prepareBrowser,
|
prepareBrowser,
|
||||||
preparePage
|
preparePage
|
||||||
} = require('./scripts/puppeteer-helper.js');
|
} = require('./scripts/puppeteer-helper.js');
|
||||||
const GameInfo = require('./scripts/classes/game-info.js').GameInfo;
|
const GameInfo = require('./scripts/classes/game-info.js');
|
||||||
const LoginResult = require('./scripts/classes/login-result.js').LoginResult;
|
const LoginResult = require('./scripts/classes/login-result.js');
|
||||||
const UserData = require('./scripts/classes/user-data.js').UserData;
|
const UserData = require('./scripts/classes/user-data.js');
|
||||||
|
|
||||||
//#region Directories
|
//#region Expose classes
|
||||||
const CACHE_PATH = './f95cache';
|
module.exports.GameInfo = GameInfo;
|
||||||
const COOKIES_SAVE_PATH = path.join(CACHE_PATH, 'cookies.json');
|
module.exports.LoginResult = LoginResult;
|
||||||
const ENGINES_SAVE_PATH = path.join(CACHE_PATH, 'engines.json');
|
module.exports.UserData = UserData;
|
||||||
const STATUSES_SAVE_PATH = path.join(CACHE_PATH, 'statuses.json');
|
//#endregion Expose classes
|
||||||
|
|
||||||
// Create directory if it doesn't exist
|
|
||||||
if (!fs.existsSync(CACHE_PATH)) fs.mkdirSync(CACHE_PATH);
|
|
||||||
//#endregion Directories
|
|
||||||
|
|
||||||
//#region Exposed properties
|
//#region Exposed properties
|
||||||
/**
|
/**
|
||||||
|
@ -44,8 +39,24 @@ module.exports.debug = function (value) {
|
||||||
module.exports.isLogged = function () {
|
module.exports.isLogged = function () {
|
||||||
return shared.isLogged;
|
return shared.isLogged;
|
||||||
};
|
};
|
||||||
|
module.exports.isolation = function(value) {
|
||||||
|
shared.isolation = value;
|
||||||
|
}
|
||||||
|
module.exports.getCacheDir = function() {
|
||||||
|
return shared.cacheDir;
|
||||||
|
}
|
||||||
|
module.exports.setCacheDir = function(value) {
|
||||||
|
shared.cacheDir = value;
|
||||||
|
|
||||||
|
// Create directory if it doesn't exist
|
||||||
|
if (!fs.existsSync(shared.cacheDir)) fs.mkdirSync(shared.cacheDir);
|
||||||
|
}
|
||||||
//#endregion Exposed properties
|
//#endregion Exposed properties
|
||||||
|
|
||||||
|
//#region Global variables
|
||||||
|
var _browser = null;
|
||||||
|
//#endregion
|
||||||
|
|
||||||
//#region Export methods
|
//#region Export methods
|
||||||
/**
|
/**
|
||||||
* @public
|
* @public
|
||||||
|
@ -77,7 +88,14 @@ module.exports.login = async function (username, password) {
|
||||||
|
|
||||||
// Else, log in throught browser
|
// Else, log in throught browser
|
||||||
if (shared.debug) console.log('No saved sessions or expired session, login on the platform');
|
if (shared.debug) console.log('No saved sessions or expired session, login on the platform');
|
||||||
let browser = await prepareBrowser();
|
|
||||||
|
let browser = null;
|
||||||
|
if (shared.isolation) browser = await prepareBrowser();
|
||||||
|
else {
|
||||||
|
if (_browser === null) _browser = await prepareBrowser();
|
||||||
|
browser = _browser;
|
||||||
|
}
|
||||||
|
|
||||||
let result = await loginF95(browser, username, password);
|
let result = await loginF95(browser, username, password);
|
||||||
shared.isLogged = result.success;
|
shared.isLogged = result.success;
|
||||||
|
|
||||||
|
@ -88,7 +106,7 @@ module.exports.login = async function (username, password) {
|
||||||
} else {
|
} else {
|
||||||
console.warn('Error during authentication: ' + result.message);
|
console.warn('Error during authentication: ' + result.message);
|
||||||
}
|
}
|
||||||
await browser.close();
|
if (shared.isolation) await browser.close();
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
|
@ -107,7 +125,13 @@ module.exports.loadF95BaseData = async function () {
|
||||||
if (shared.debug) console.log('Loading base data...');
|
if (shared.debug) console.log('Loading base data...');
|
||||||
|
|
||||||
// Prepare a new web page
|
// Prepare a new web page
|
||||||
let browser = await prepareBrowser();
|
let browser = null;
|
||||||
|
if (shared.isolation) browser = await prepareBrowser();
|
||||||
|
else {
|
||||||
|
if (_browser === null) _browser = await prepareBrowser();
|
||||||
|
browser = _browser;
|
||||||
|
}
|
||||||
|
|
||||||
let page = await preparePage(browser); // Set new isolated page
|
let page = await preparePage(browser); // Set new isolated page
|
||||||
await page.setCookie(...shared.cookies); // Set cookies to avoid login
|
await page.setCookie(...shared.cookies); // Set cookies to avoid login
|
||||||
|
|
||||||
|
@ -119,18 +143,18 @@ module.exports.loadF95BaseData = async function () {
|
||||||
// Obtain engines (disc/online)
|
// Obtain engines (disc/online)
|
||||||
await page.waitForSelector(constSelectors.ENGINE_ID_SELECTOR);
|
await page.waitForSelector(constSelectors.ENGINE_ID_SELECTOR);
|
||||||
shared.engines = await loadValuesFromLatestPage(page,
|
shared.engines = await loadValuesFromLatestPage(page,
|
||||||
ENGINES_SAVE_PATH,
|
shared.enginesCachePath,
|
||||||
constSelectors.ENGINE_ID_SELECTOR,
|
constSelectors.ENGINE_ID_SELECTOR,
|
||||||
'engines');
|
'engines');
|
||||||
|
|
||||||
// Obtain statuses (disc/online)
|
// Obtain statuses (disc/online)
|
||||||
await page.waitForSelector(constSelectors.STATUS_ID_SELECTOR);
|
await page.waitForSelector(constSelectors.STATUS_ID_SELECTOR);
|
||||||
shared.statuses = await loadValuesFromLatestPage(page,
|
shared.statuses = await loadValuesFromLatestPage(page,
|
||||||
STATUSES_SAVE_PATH,
|
shared.statusesCachePath,
|
||||||
constSelectors.STATUS_ID_SELECTOR,
|
constSelectors.STATUS_ID_SELECTOR,
|
||||||
'statuses');
|
'statuses');
|
||||||
|
|
||||||
await browser.close();
|
if (shared.isolation) await browser.close();
|
||||||
if (shared.debug) console.log('Base data loaded');
|
if (shared.debug) console.log('Base data loaded');
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -169,7 +193,12 @@ module.exports.getGameData = async function (name, includeMods) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Gets the search results of the game being searched for
|
// Gets the search results of the game being searched for
|
||||||
let browser = await prepareBrowser();
|
let browser = null;
|
||||||
|
if (shared.isolation) browser = await prepareBrowser();
|
||||||
|
else {
|
||||||
|
if (_browser === null) _browser = await prepareBrowser();
|
||||||
|
browser = _browser;
|
||||||
|
}
|
||||||
let urlList = await getSearchGameResults(browser, name);
|
let urlList = await getSearchGameResults(browser, name);
|
||||||
|
|
||||||
// Process previous partial results
|
// Process previous partial results
|
||||||
|
@ -187,7 +216,7 @@ module.exports.getGameData = async function (name, includeMods) {
|
||||||
else result.push(info);
|
else result.push(info);
|
||||||
}
|
}
|
||||||
|
|
||||||
await browser.close();
|
if (shared.isolation) await browser.close();
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
|
@ -202,7 +231,12 @@ module.exports.getUserData = async function () {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Prepare a new web page
|
// Prepare a new web page
|
||||||
let browser = await prepareBrowser();
|
let browser = null;
|
||||||
|
if (shared.isolation) browser = await prepareBrowser();
|
||||||
|
else {
|
||||||
|
if (_browser === null) _browser = await prepareBrowser();
|
||||||
|
browser = _browser;
|
||||||
|
}
|
||||||
let page = await preparePage(browser); // Set new isolated page
|
let page = await preparePage(browser); // Set new isolated page
|
||||||
await page.setCookie(...shared.cookies); // Set cookies to avoid login
|
await page.setCookie(...shared.cookies); // Set cookies to avoid login
|
||||||
await page.goto(constURLs.F95_BASE_URL); // Go to base page
|
await page.goto(constURLs.F95_BASE_URL); // Go to base page
|
||||||
|
@ -227,7 +261,7 @@ module.exports.getUserData = async function () {
|
||||||
ud.watchedThreads = await threads;
|
ud.watchedThreads = await threads;
|
||||||
|
|
||||||
await page.close();
|
await page.close();
|
||||||
await browser.close();
|
if (shared.isolation) await browser.close();
|
||||||
|
|
||||||
return ud;
|
return ud;
|
||||||
}
|
}
|
||||||
|
@ -247,9 +281,9 @@ module.exports.logout = function() {
|
||||||
*/
|
*/
|
||||||
function loadCookies() {
|
function loadCookies() {
|
||||||
// Check the existence of the cookie file
|
// Check the existence of the cookie file
|
||||||
if (fs.existsSync(COOKIES_SAVE_PATH)) {
|
if (fs.existsSync(shared.cookiesCachePath)) {
|
||||||
// Read cookies
|
// Read cookies
|
||||||
let cookiesJSON = fs.readFileSync(COOKIES_SAVE_PATH);
|
let cookiesJSON = fs.readFileSync(shared.cookiesCachePath);
|
||||||
let cookies = JSON.parse(cookiesJSON);
|
let cookies = JSON.parse(cookiesJSON);
|
||||||
|
|
||||||
// Check if the cookies have expired
|
// Check if the cookies have expired
|
||||||
|
@ -376,7 +410,7 @@ async function loginF95(browser, username, password) {
|
||||||
// Save cookies to avoid re-auth
|
// Save cookies to avoid re-auth
|
||||||
if (result.success) {
|
if (result.success) {
|
||||||
let c = await page.cookies();
|
let c = await page.cookies();
|
||||||
fs.writeFileSync(COOKIES_SAVE_PATH, JSON.stringify(c));
|
fs.writeFileSync(shared.cookiesCachePath, JSON.stringify(c));
|
||||||
result.message = 'Authentication successful';
|
result.message = 'Authentication successful';
|
||||||
}
|
}
|
||||||
// Obtain the error message
|
// Obtain the error message
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
class GameDownload {
|
class GameDownload {
|
||||||
constructor() {
|
constructor() {
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +32,7 @@ class GameDownload {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
module.exports.GameDownload = GameDownload;
|
module.exports = GameDownload;
|
||||||
|
|
||||||
function downloadMEGA(url){
|
function downloadMEGA(url){
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,10 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
const UNKNOWN = 'Unknown';
|
const UNKNOWN = 'Unknown';
|
||||||
|
|
||||||
class GameInfo {
|
class GameInfo {
|
||||||
constructor() {
|
constructor() {
|
||||||
|
//#region Properties
|
||||||
/**
|
/**
|
||||||
* Game name
|
* Game name
|
||||||
* @type String
|
* @type String
|
||||||
|
@ -68,9 +71,13 @@ class GameInfo {
|
||||||
*/
|
*/
|
||||||
this.gameDir = UNKNOWN;
|
this.gameDir = UNKNOWN;
|
||||||
/**
|
/**
|
||||||
*
|
* Information on game file download links,
|
||||||
|
* including information on hosting platforms
|
||||||
|
* and operating system supported by the specific link
|
||||||
|
* @type GameDownload[]
|
||||||
*/
|
*/
|
||||||
this.downloadInfo = [];
|
this.downloadInfo = [];
|
||||||
|
//#endregion Properties
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -89,7 +96,8 @@ class GameInfo {
|
||||||
lastUpdate: this.lastUpdate,
|
lastUpdate: this.lastUpdate,
|
||||||
lastPlayed: this.lastPlayed,
|
lastPlayed: this.lastPlayed,
|
||||||
isMod: this.isMod,
|
isMod: this.isMod,
|
||||||
gameDir: this.gameDir
|
gameDir: this.gameDir,
|
||||||
|
downloadInfo: this.downloadInfo
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -102,4 +110,4 @@ class GameInfo {
|
||||||
return Object.assign(new GameInfo(), json);
|
return Object.assign(new GameInfo(), json);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
module.exports.GameInfo = GameInfo;
|
module.exports = GameInfo;
|
|
@ -1,3 +1,5 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Object obtained in response to an attempt to login to the portal.
|
* Object obtained in response to an attempt to login to the portal.
|
||||||
*/
|
*/
|
||||||
|
@ -15,4 +17,4 @@ class LoginResult {
|
||||||
this.message = '';
|
this.message = '';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
module.exports.LoginResult = LoginResult;
|
module.exports = LoginResult;
|
|
@ -1,3 +1,5 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class containing the data of the user currently connected to the F95Zone platform.
|
* Class containing the data of the user currently connected to the F95Zone platform.
|
||||||
*/
|
*/
|
||||||
|
@ -21,4 +23,4 @@ class UserData {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
module.exports.UserData = UserData;
|
module.exports = UserData;
|
|
@ -1,3 +1,5 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
// Public modules from npm
|
// Public modules from npm
|
||||||
const HTMLParser = require('node-html-parser');
|
const HTMLParser = require('node-html-parser');
|
||||||
const puppeteer = require('puppeteer');
|
const puppeteer = require('puppeteer');
|
||||||
|
@ -7,8 +9,8 @@ const urlExist = require('url-exist');
|
||||||
const shared = require('./shared.js');
|
const shared = require('./shared.js');
|
||||||
const selectors = require('./costants/css-selectors.js');
|
const selectors = require('./costants/css-selectors.js');
|
||||||
const { preparePage } = require('./puppeteer-helper.js');
|
const { preparePage } = require('./puppeteer-helper.js');
|
||||||
const GameDownload = require('./classes/game-download.js').GameDownload;
|
const GameDownload = require('./classes/game-download.js');
|
||||||
const GameInfo = require('./classes/game-info.js').GameInfo;
|
const GameInfo = require('./classes/game-info.js');
|
||||||
const { isStringAValidURL, isF95URL } = require('./urls-helper.js');
|
const { isStringAValidURL, isF95URL } = require('./urls-helper.js');
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -154,8 +156,8 @@ async function getGamePreviewSource(page) {
|
||||||
// Get the firs image available
|
// Get the firs image available
|
||||||
let img = document.querySelector(selector);
|
let img = document.querySelector(selector);
|
||||||
|
|
||||||
if (img === null || img === undefined) return null;
|
if (img) return img.getAttribute('src');
|
||||||
else return img.getAttribute('src');
|
else return null;
|
||||||
}, selectors.GAME_IMAGES);
|
}, selectors.GAME_IMAGES);
|
||||||
|
|
||||||
// Check if the URL is valid
|
// Check if the URL is valid
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
// Public modules from npm
|
// Public modules from npm
|
||||||
const puppeteer = require('puppeteer');
|
const puppeteer = require('puppeteer');
|
||||||
|
|
||||||
|
|
|
@ -1,71 +1,155 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
// Core modules
|
||||||
|
const { join } = require('path');
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class containing variables shared between modules.
|
* Class containing variables shared between modules.
|
||||||
*/
|
*/
|
||||||
class Shared {
|
class Shared {
|
||||||
|
//#region Properties
|
||||||
/**
|
/**
|
||||||
* Shows log messages and other useful functions for module debugging.
|
* Shows log messages and other useful functions for module debugging.
|
||||||
|
* @type Boolean
|
||||||
*/
|
*/
|
||||||
static _debug = false;
|
static _debug = false;
|
||||||
|
/**
|
||||||
|
* Indicates whether a user is logged in to the F95Zone platform or not.
|
||||||
|
* @type Boolean
|
||||||
|
*/
|
||||||
static _isLogged = false;
|
static _isLogged = false;
|
||||||
|
/**
|
||||||
|
* List of cookies obtained from the F95Zone platform.
|
||||||
|
* @type Object[]
|
||||||
|
*/
|
||||||
static _cookies = null;
|
static _cookies = null;
|
||||||
|
/**
|
||||||
|
* List of possible game engines used for development.
|
||||||
|
* @type String[]
|
||||||
|
*/
|
||||||
static _engines = null;
|
static _engines = null;
|
||||||
|
/**
|
||||||
|
* List of possible development statuses that a game can assume.
|
||||||
|
* @type String[]
|
||||||
|
*/
|
||||||
static _statuses = null;
|
static _statuses = null;
|
||||||
|
/**
|
||||||
|
* Wait instruction for the browser created by puppeteer.
|
||||||
|
* @type String
|
||||||
|
*/
|
||||||
static WAIT_STATEMENT = 'domcontentloaded';
|
static WAIT_STATEMENT = 'domcontentloaded';
|
||||||
|
/**
|
||||||
|
* Path to the directory to save the cache generated by the API.
|
||||||
|
* @type String
|
||||||
|
*/
|
||||||
|
static _cacheDir = './f95cache';
|
||||||
|
/**
|
||||||
|
* If true, it opens a new browser for each request to
|
||||||
|
* the F95Zone platform, otherwise it reuses the same.
|
||||||
|
* @type Boolean
|
||||||
|
*/
|
||||||
|
static _isolation = false;
|
||||||
|
//#endregion Properties
|
||||||
|
|
||||||
static set debug(val) {
|
//#region Getters
|
||||||
this._debug = val;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shows log messages and other useful functions for module debugging.
|
* Shows log messages and other useful functions for module debugging.
|
||||||
* @returns {boolean}
|
* @returns {Boolean}
|
||||||
*/
|
*/
|
||||||
static get debug() {
|
static get debug() {
|
||||||
return this._debug;
|
return this._debug;
|
||||||
}
|
}
|
||||||
|
|
||||||
static set isLogged(val) {
|
|
||||||
this._isLogged = val;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @returns {boolean}
|
* @returns {boolean}
|
||||||
*/
|
*/
|
||||||
static get isLogged() {
|
static get isLogged() {
|
||||||
return this._isLogged;
|
return this._isLogged;
|
||||||
}
|
}
|
||||||
|
|
||||||
static set cookies(val) {
|
|
||||||
this._cookies = val;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @returns {object[]}
|
* @returns {object[]}
|
||||||
*/
|
*/
|
||||||
static get cookies() {
|
static get cookies() {
|
||||||
return this._cookies;
|
return this._cookies;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* @returns {String[]}
|
||||||
|
*/
|
||||||
|
static get engines() {
|
||||||
|
return this._engines;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @returns {String[]}
|
||||||
|
*/
|
||||||
|
static get statuses() {
|
||||||
|
return this._statuses;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Directory to save the API cache.
|
||||||
|
* @returns {String}
|
||||||
|
*/
|
||||||
|
static get cacheDir() {
|
||||||
|
return this._cacheDir;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Path to the F95 platform cache.
|
||||||
|
* @returns {String}
|
||||||
|
*/
|
||||||
|
static get cookiesCachePath() {
|
||||||
|
return join(this._cacheDir, 'cookies.json');
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Path to the game engine cache.
|
||||||
|
* @returns {String}
|
||||||
|
*/
|
||||||
|
static get enginesCachePath() {
|
||||||
|
return join(this._cacheDir, 'engines.json');
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Path to the cache of possible game states.
|
||||||
|
* @returns {String}
|
||||||
|
*/
|
||||||
|
static get statusesCachePath() {
|
||||||
|
return join(this._cacheDir, 'statuses.json');
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* If true, it opens a new browser for each request
|
||||||
|
* to the F95Zone platform, otherwise it reuses the same.
|
||||||
|
* @returns {Boolean}
|
||||||
|
*/
|
||||||
|
static get isolation() {
|
||||||
|
return this._isolation;
|
||||||
|
}
|
||||||
|
//#endregion Getters
|
||||||
|
|
||||||
|
//#region Setters
|
||||||
|
static set cookies(val) {
|
||||||
|
this._cookies = val;
|
||||||
|
}
|
||||||
|
|
||||||
static set engines(val) {
|
static set engines(val) {
|
||||||
this._engines = val;
|
this._engines = val;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @returns {string[]}
|
|
||||||
*/
|
|
||||||
static get engines() {
|
|
||||||
return this._engines;
|
|
||||||
}
|
|
||||||
|
|
||||||
static set statuses(val) {
|
static set statuses(val) {
|
||||||
this._statuses = val;
|
this._statuses = val;
|
||||||
}
|
}
|
||||||
/**
|
|
||||||
* @returns {string[]}
|
static set cacheDir(val) {
|
||||||
*/
|
this._cacheDir = val;
|
||||||
static get statuses() {
|
|
||||||
return this._statuses;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static set debug(val) {
|
||||||
|
this._debug = val;
|
||||||
|
}
|
||||||
|
|
||||||
|
static set isLogged(val) {
|
||||||
|
this._isLogged = val;
|
||||||
|
}
|
||||||
|
|
||||||
|
static set isolation(val) {
|
||||||
|
this._isolation = val;
|
||||||
|
}
|
||||||
|
//#endregion Setters
|
||||||
}
|
}
|
||||||
|
|
||||||
module.exports = Shared;
|
module.exports = Shared;
|
|
@ -1,7 +1,8 @@
|
||||||
|
'use strict';
|
||||||
|
|
||||||
// Modules from file
|
// Modules from file
|
||||||
const { F95_BASE_URL } = require('./costants/urls.js');
|
const { F95_BASE_URL } = require('./costants/urls.js');
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @protected
|
* @protected
|
||||||
* Check if the url belongs to the domain of the F95 platform.
|
* Check if the url belongs to the domain of the F95 platform.
|
||||||
|
|
Binary file not shown.
|
@ -3,9 +3,16 @@
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
"description": "Unofficial Node JS module for scraping F95Zone platform",
|
"description": "Unofficial Node JS module for scraping F95Zone platform",
|
||||||
"main": "./app/index.js",
|
"main": "./app/index.js",
|
||||||
|
"repository": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/MillenniumEarl/F95API.git"
|
||||||
|
},
|
||||||
|
"license": "UNLICENSED",
|
||||||
|
"private": true,
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"unit-test": "nyc --reporter=text mocha",
|
"unit-test": "nyc --reporter=text mocha",
|
||||||
"test": "node ./app/test.js"
|
"test": "node ./app/test.js",
|
||||||
|
"deploy": "npm pack"
|
||||||
},
|
},
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"f95zone",
|
"f95zone",
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
const expect = require("chai").expect;
|
const expect = require("chai").expect;
|
||||||
const F95API = require("../app/index");
|
const F95API = require("../app/index");
|
||||||
const fs = require("fs");
|
const fs = require("fs");
|
||||||
const { debug } = require("console");
|
|
||||||
|
|
||||||
const COOKIES_SAVE_PATH = "./f95cache/cookies.json";
|
const COOKIES_SAVE_PATH = "./f95cache/cookies.json";
|
||||||
const ENGINES_SAVE_PATH = "./f95cache/engines.json";
|
const ENGINES_SAVE_PATH = "./f95cache/engines.json";
|
||||||
|
@ -11,6 +10,8 @@ const PASSWORD = "f9vTcRNuvxj4YpK";
|
||||||
const FAKE_USERNAME = "FakeUsername091276";
|
const FAKE_USERNAME = "FakeUsername091276";
|
||||||
const FAKE_PASSWORD = "fake_password";
|
const FAKE_PASSWORD = "fake_password";
|
||||||
|
|
||||||
|
F95API.isolation(true);
|
||||||
|
|
||||||
describe("Login without cookies", function () {
|
describe("Login without cookies", function () {
|
||||||
//#region Set-up
|
//#region Set-up
|
||||||
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
||||||
|
@ -48,7 +49,7 @@ describe("Login with cookies", function () {
|
||||||
//#region Set-up
|
//#region Set-up
|
||||||
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
||||||
|
|
||||||
before("Log in to create cookies", async function () {
|
before("Log in to create cookies then logout", async function () {
|
||||||
// Runs once before the first test in this block
|
// Runs once before the first test in this block
|
||||||
if (!fs.existsSync(COOKIES_SAVE_PATH)) await F95API.login(USERNAME, PASSWORD); // Download cookies
|
if (!fs.existsSync(COOKIES_SAVE_PATH)) await F95API.login(USERNAME, PASSWORD); // Download cookies
|
||||||
F95API.logout();
|
F95API.logout();
|
||||||
|
@ -127,4 +128,51 @@ describe("Search game data", function () {
|
||||||
const result = await F95API.getGameData("Kingdom of Deception", false);
|
const result = await F95API.getGameData("Kingdom of Deception", false);
|
||||||
expect(result, "Without being logged should return null").to.be.null;
|
expect(result, "Without being logged should return null").to.be.null;
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("Load user data", function () {
|
||||||
|
//#region Set-up
|
||||||
|
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
||||||
|
//#endregion Set-up
|
||||||
|
|
||||||
|
it("Retrieve when logged", async function () {
|
||||||
|
// Login
|
||||||
|
await F95API.login(USERNAME, PASSWORD);
|
||||||
|
|
||||||
|
// Then retrieve user data
|
||||||
|
let data = await F95API.getUserData();
|
||||||
|
|
||||||
|
expect(data).to.exist;
|
||||||
|
expect(data.username).to.equal(USERNAME);
|
||||||
|
});
|
||||||
|
it("Retrieve when not logged", async function () {
|
||||||
|
// Logout
|
||||||
|
F95API.logout();
|
||||||
|
|
||||||
|
// Try to retrieve user data
|
||||||
|
let data = await F95API.getUserData();
|
||||||
|
|
||||||
|
expect(data).to.be.null;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("Check game version", function () {
|
||||||
|
//#region Set-up
|
||||||
|
this.timeout(30000); // All tests in this suite get 30 seconds before timeout
|
||||||
|
//#endregion Set-up
|
||||||
|
|
||||||
|
it("Get game version", async function () {
|
||||||
|
const loginResult = await F95API.login(USERNAME, PASSWORD);
|
||||||
|
expect(loginResult.success).to.be.true;
|
||||||
|
|
||||||
|
const loadResult = await F95API.loadF95BaseData();
|
||||||
|
expect(loadResult).to.be.true;
|
||||||
|
|
||||||
|
// This test depend on the data on F95Zone at
|
||||||
|
// https://f95zone.to/threads/kingdom-of-deception-v0-10-8-hreinn-games.2733/
|
||||||
|
const result = (await F95API.getGameData("Kingdom of Deception", false))[0];
|
||||||
|
|
||||||
|
let version = await F95API.getGameVersion(result);
|
||||||
|
expect(version).to.be.equal(result.version);
|
||||||
|
});
|
||||||
});
|
});
|
Loading…
Reference in New Issue