mirror of
https://github.com/tiennm99/is-a-good-dev.git
synced 2026-09-09 04:17:27 +00:00
feat(ci): move to dnscontrol
This commit is contained in:
+2
-2
@@ -2,5 +2,5 @@
|
||||
|
||||
/sub-logs/* @is-a-good-dev/helpers
|
||||
/.github/* @Tweak4141
|
||||
/scripts/* @Tweak4141
|
||||
/utils/* @Tweak4141
|
||||
/.github/workflows/* @Tweak4141 @wdhdev
|
||||
/dnsconfig.js @Tweak4141 @wdhdev
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
name: Publish
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- "sub-logs/*"
|
||||
- ".github/workflows/publish.yml"
|
||||
- "dnsconfig.js"
|
||||
|
||||
workflow_dispatch:
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.ref }}-publish
|
||||
cancel-in-progress: false
|
||||
|
||||
jobs:
|
||||
dns:
|
||||
name: DNS
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Generate creds.json
|
||||
run: echo '{"cloudflare":{"TYPE":"CLOUDFLAREAPI","apitoken":"$CLOUDFLARE_API_TOKEN"}}' > ./creds.json
|
||||
|
||||
- name: Publish
|
||||
uses: is-a-dev/dnscontrol-action@main
|
||||
env:
|
||||
CLOUDFLARE_API_TOKEN: ${{ secrets.API_KEY }}
|
||||
with:
|
||||
args: push
|
||||
@@ -1,33 +0,0 @@
|
||||
name: Update Records
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
|
||||
jobs:
|
||||
validation:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
with:
|
||||
fetch-depth: 0
|
||||
- uses: actions/setup-node@v3
|
||||
with:
|
||||
node-version: 16
|
||||
- name: Get Files
|
||||
id: changed-files
|
||||
uses: tj-actions/changed-files@v34
|
||||
with:
|
||||
files: |
|
||||
sub-logs/**
|
||||
reserved/**
|
||||
- name: Install Modules
|
||||
if: steps.changed-files.outputs.any_changed == 'true'
|
||||
run: yarn
|
||||
- name: Publish Records
|
||||
if: steps.changed-files.outputs.any_changed == 'true'
|
||||
id: tests
|
||||
run: yarn add-records
|
||||
env:
|
||||
API_KEY: ${{ secrets.API_KEY }}
|
||||
FILES: ${{ steps.changed-files.outputs.all_changed_files }}
|
||||
actions_path: ${{ github.workspace }}
|
||||
@@ -0,0 +1,42 @@
|
||||
name: Validation
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- "sub-logs/*"
|
||||
- ".github/workflows/validation.yml"
|
||||
- "dnsconfig.js"
|
||||
|
||||
workflow_dispatch:
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.ref }}-validation
|
||||
cancel-in-progress: true
|
||||
|
||||
jobs:
|
||||
dns:
|
||||
name: DNS
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Check
|
||||
uses: is-a-dev/dnscontrol-action@main
|
||||
with:
|
||||
args: check
|
||||
|
||||
json:
|
||||
name: JSON
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: JSON Syntax Check
|
||||
uses: limitusus/json-syntax-check@v2
|
||||
with:
|
||||
pattern: "\\.json$"
|
||||
env:
|
||||
BASE: "domains/"
|
||||
@@ -1,45 +0,0 @@
|
||||
name: Validation
|
||||
on: [pull_request]
|
||||
|
||||
jobs:
|
||||
validation:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
with:
|
||||
fetch-depth: 0
|
||||
- name: Get Files
|
||||
id: changed-files
|
||||
uses: tj-actions/changed-files@v34
|
||||
with:
|
||||
files: |
|
||||
sub-logs/**
|
||||
reserved/**
|
||||
- name: Install Modules
|
||||
if: steps.changed-files.outputs.any_changed == 'true'
|
||||
run: yarn
|
||||
- name: Run Tests
|
||||
if: steps.changed-files.outputs.any_changed == 'true'
|
||||
id: tests
|
||||
run: yarn test
|
||||
env:
|
||||
FILES: ${{ steps.changed-files.outputs.all_changed_files }}
|
||||
actions_path: ${{ github.workspace }}
|
||||
- name: Comment
|
||||
if: steps.tests.outputs.shouldComment == 'true'
|
||||
uses: mshick/add-pr-comment@v1
|
||||
with:
|
||||
message: |
|
||||
## Validation Results
|
||||
| Information Validation | Record Validation |
|
||||
|-|-|
|
||||
| ${{steps.tests.outputs.infoMessage}} ${{steps.tests.outputs.infoReason}} | ${{steps.tests.outputs.recordMessage}} ${{steps.tests.outputs.recordInfo}} |
|
||||
|
||||
### JSON File Content
|
||||
```json
|
||||
${{steps.tests.outputs.jsonData}}
|
||||
```
|
||||
repo-token: ${{ secrets.GITHUB_TOKEN }}
|
||||
proxy-url: https://is-a-good-dev-gh-proxy.talosbot.xyz/
|
||||
repo-token-user-login: 'github-actions[bot]' # The user.login for temporary GitHub tokens
|
||||
allow-repeats: false # Default: false
|
||||
@@ -1,3 +0,0 @@
|
||||
node_modules/
|
||||
dist/
|
||||
package-lock.json
|
||||
@@ -0,0 +1,53 @@
|
||||
function getDomainsList(filesPath) {
|
||||
var result = [];
|
||||
var files = glob.apply(null, [filesPath, true, ".json"]);
|
||||
|
||||
for (var i = 0; i < files.length; i++) {
|
||||
var name = files[i].split("/").pop().replace(/\.json$/, "");
|
||||
|
||||
result.push({ name: name, data: require(files[i]) });
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
var domains = getDomainsList("./sub-logs");
|
||||
var commit = [];
|
||||
|
||||
for (var subdomain in domains) {
|
||||
var subdomainName = domains[subdomain].name;
|
||||
var domainData = domains[subdomain].data;
|
||||
var proxyState = domainData.proxied ? { cloudflare_proxy: "on" } : { cloudflare_proxy: "off" };
|
||||
|
||||
// Handle A records
|
||||
if (domainData.record.A) {
|
||||
for (var a in domainData.record.A.value) {
|
||||
commit.push(A(domainData.record.A.name, IP(domainData.record.A.value[a]), proxyState));
|
||||
}
|
||||
}
|
||||
|
||||
// Handle AAAA records
|
||||
if (domainData.record.AAAA) {
|
||||
for (var aaaa in domainData.record.AAAA.value) {
|
||||
commit.push(AAAA(domainData.record.AAAA.name, domainData.record.AAAA.value[aaaa], proxyState));
|
||||
}
|
||||
}
|
||||
|
||||
// Handle CNAME records
|
||||
if (domainData.record.CNAME) {
|
||||
// Allow CNAME record on root
|
||||
if (subdomainName === "@") {
|
||||
commit.push(ALIAS(subdomainName, domainData.record.CNAME + ".", proxyState));
|
||||
} else {
|
||||
commit.push(CNAME(domainData.record.CNAME.name, domainData.record.CNAME.value + ".", proxyState));
|
||||
}
|
||||
}
|
||||
|
||||
// Handle TXT records
|
||||
if (domainData.record.TXT) {
|
||||
commit.push(TXT(domainData.record.TXT.name === "@" ? subdomainName : domainData.record.TXT.name + "." + subdomainName, domainData.record.TXT.value));
|
||||
}
|
||||
}
|
||||
|
||||
// Commit all DNS records
|
||||
D("is-a-good.dev", NewRegistrar("none"), DnsProvider(NewDnsProvider("cloudflare")), commit);
|
||||
@@ -1,35 +0,0 @@
|
||||
const fetch = require('node-fetch');
|
||||
const getJSON = require('../utils/getJSON.js');
|
||||
const data = getJSON(process.env.FILES);
|
||||
const arrayRecordTypes = ["a", "aaaa"];
|
||||
async function addRecord(type, name, value) {
|
||||
const response = await fetch(`https://api.is-a-good.dev/api/is-a-good-dev/zones/add?apiKey=${process.env.API_KEY}&type=${type.toUpperCase()}&name=${name}&content=${value}`);
|
||||
const data = await response.json();
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
(async () => {
|
||||
try {
|
||||
if (!data) return;
|
||||
|
||||
const records = Object.keys(data.target);
|
||||
for (const i in records) {
|
||||
const recordType = records[i];
|
||||
const name = data.target[recordType].name;
|
||||
const value = data.target[recordType].value;
|
||||
console.log(`Adding record type ${recordType} with values ${name}, ${value}`);
|
||||
if (arrayRecordTypes.includes(recordType.toLowerCase()) != true) {
|
||||
let res = await addRecord(recordType, name, value);
|
||||
return console.log(res);
|
||||
}
|
||||
for (const ip of value) {
|
||||
let res = await addRecord(recordType, name, ip);
|
||||
console.log(res);
|
||||
}
|
||||
}
|
||||
} catch(e) {
|
||||
console.log('Failed to add records.');
|
||||
console.log(e);
|
||||
}
|
||||
})();
|
||||
@@ -9,7 +9,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "aniruddh",
|
||||
"value": "23.94.14.190"
|
||||
"value": ["23.94.14.190"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "anya",
|
||||
"value": "87.98.164.155"
|
||||
"value": ["87.98.164.155"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "arman",
|
||||
"value": "89.106.200.1"
|
||||
"value": ["89.106.200.1"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
},
|
||||
|
||||
"TXT": {
|
||||
"name": "asuid.avengers-sonarqube",
|
||||
"name": "asuid",
|
||||
"value": "2ADF2B3BF4F2D427644C6A908F1607F17C2A1AAE36C1A5E86A6FDFD7B56B2149"
|
||||
}
|
||||
},
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "ionetty",
|
||||
"value": "66.94.121.50"
|
||||
"value": ["66.94.121.50"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"owner": {
|
||||
"username": "michaelbelete",
|
||||
"email": "it.michael.belete@gmail.com"
|
||||
},
|
||||
|
||||
"target": {
|
||||
"TXT": {
|
||||
"name": "michaelbelete",
|
||||
"value": "vc-domain-verify=michaelbelete.is-a-good.dev,c5ef3d006ace4ff62d3e"
|
||||
}
|
||||
},
|
||||
|
||||
"proxied": false
|
||||
}
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "oreki",
|
||||
"value": "164.132.74.251"
|
||||
"value": ["164.132.74.251"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "paul",
|
||||
"value": "192.95.42.75"
|
||||
"value": ["192.95.42.75"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "Raja",
|
||||
"value": "43.204.88.80"
|
||||
"value": ["43.204.88.80"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "rehanplayz",
|
||||
"value": "198.251.81.131"
|
||||
"value": ["198.251.81.131"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "redirect",
|
||||
"value": "52.72.49.79"
|
||||
"value": ["52.72.49.79"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -7,11 +7,11 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "themediocre",
|
||||
"value": "34.132.134.162"
|
||||
"value": ["34.132.134.162"]
|
||||
},
|
||||
|
||||
"TXT": {
|
||||
"name": "themediocre",
|
||||
"name": "@",
|
||||
"value": "replit-verify=7a770ba4-a691-4406-b81a-e009a792e0ae"
|
||||
}
|
||||
},
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
},
|
||||
|
||||
"TXT": {
|
||||
"name": "_github-pages-challenge-vuquangthinh.tonywu",
|
||||
"name": "_github-pages-challenge-vuquangthinh",
|
||||
"value": "0b9dc3e2752d1dc520c401ce8b7557"
|
||||
}
|
||||
},
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
"target": {
|
||||
"A": {
|
||||
"name": "vishal",
|
||||
"value": "43.205.87.144"
|
||||
"value": ["43.205.87.144"]
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -1,61 +0,0 @@
|
||||
const core = require('@actions/core');
|
||||
const getJSON = require('../utils/getJSON.js');
|
||||
const checkInfo = require('../utils/checkInfo.js');
|
||||
const checkRecords = require('../utils/checkRecords.js');
|
||||
const getFileName = require('../utils/getFileName.js');
|
||||
const data = getJSON(process.env.FILES);
|
||||
|
||||
function setupMessages() {
|
||||
core.setOutput('infoMessage', "Could not validate info.");
|
||||
core.setOutput('recordMessage', "Could not validate records.");
|
||||
core.setOutput('jsonData', JSON.stringify(data, null, 2))
|
||||
core.setOutput('shouldComment', 'true')
|
||||
};
|
||||
|
||||
function outputInvalidJsonFile() {
|
||||
core.setOutput('infoMessage', "Could not validate info.");
|
||||
core.setOutput('recordMessage', "Could not validate records.");
|
||||
core.setOutput('jsonData', "Could not read the JSON file, did you have an error in your syntax?")
|
||||
core.setOutput('shouldComment', 'true')
|
||||
}
|
||||
|
||||
beforeAll(() => {
|
||||
setupMessages();
|
||||
if (data == 3) {
|
||||
outputInvalidJsonFile();
|
||||
|
||||
console.log("ERROR: JSON file is invalid. Either the file is not JSON, or there is an error in the JSON syntax.");
|
||||
return process.exit(1)
|
||||
};
|
||||
|
||||
if (data == false) {
|
||||
core.setOutput('shouldComment', 'false')
|
||||
console.log('INFO: File is not a subdomain JSON file.')
|
||||
return process.exit(0)
|
||||
};
|
||||
});
|
||||
|
||||
test('check if json file has required info', async () => {
|
||||
const passed = await checkInfo(data);
|
||||
let infoMessage = passed === true ? "Valid information provided." : passed === "unknown" ? "Error verifying email address.\nA maintainer will have to manually verify your email address.\nReason:" : "Invalid information provided.\nPlease check your provided information.\nReason:";
|
||||
|
||||
core.setOutput('infoMessage', infoMessage);
|
||||
expect(passed).toBeTruthy();
|
||||
}, 15000);
|
||||
|
||||
test('Check if JSON file follows format', () => {
|
||||
const passed = checkRecords(data);
|
||||
let recordMessage = passed === true ? "Valid records provided." : "Invalid records provided.\nPlease check your provided records.\nThey should only be of type `A`, `CNAME` or `TXT`, and should follow their respective formats.";
|
||||
|
||||
core.setOutput('recordMessage', recordMessage);
|
||||
expect(passed).toBe(true);
|
||||
});
|
||||
|
||||
test('Check if JSON file matches the value name', () => {
|
||||
const passed = getFileName(process.env.FILES, data);
|
||||
|
||||
let fileNameMessage = passed === true ? "File name matches target.RECORD_TYPE." : "File name does not match any target.RECORD_TYPE.";
|
||||
|
||||
core.setOutput('fileNameMessage', fileNameMessage);
|
||||
expect(passed).toBe(true);
|
||||
});
|
||||
@@ -1,27 +0,0 @@
|
||||
const fetch = require('node-fetch');
|
||||
const core = require('@actions/core');
|
||||
|
||||
async function checkEmail(email) {
|
||||
console.log(`Checking: ${email}`);
|
||||
|
||||
const url = `https://api.is-a-good.dev/email-check?key=6lPyUV2dX8&email=${encodeURIComponent(email)}`;
|
||||
|
||||
const options = {
|
||||
method: 'GET'
|
||||
}
|
||||
|
||||
const res = await fetch(url, options).then(res => res.json());
|
||||
console.log(res);
|
||||
|
||||
core.setOutput('infoReason', res.reason);
|
||||
|
||||
if (res.data.valid) return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
async function checkInfo(data) {
|
||||
return await checkEmail(data.owner.email);
|
||||
}
|
||||
|
||||
module.exports = checkInfo;
|
||||
@@ -1,35 +0,0 @@
|
||||
const { checkIfValidIP, checkIfValidIPv6, checkIfValidFQDN, checkInvalidDomain, isString } = require('./utils.js');
|
||||
|
||||
function checkRecords(data) {
|
||||
const recordType = Object.keys(data.target)[0];
|
||||
const value = data.target[recordType].value;
|
||||
// Check if the domain is invalid
|
||||
if (checkInvalidDomain(data.target[recordType].name) === true) return false;
|
||||
|
||||
// Check AAAA record
|
||||
if (recordType.toLowerCase() === 'aaaa') {
|
||||
if (!Array.isArray(value)) return false;
|
||||
for (const record of value) {
|
||||
if (checkIfValidIPv6(record) == false) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
// Check A record
|
||||
if (recordType.toLowerCase() === 'a') {
|
||||
if (!Array.isArray(value)) return false;
|
||||
for (const record of value) {
|
||||
if (checkIfValidIP(record) == false) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// Check CNAME record
|
||||
if (recordType.toLowerCase() === 'cname') {
|
||||
if (!isString(value)) return false;
|
||||
return checkIfValidFQDN(value);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
module.exports = checkRecords;
|
||||
@@ -1,13 +0,0 @@
|
||||
const { stripExt } = require('./utils.js');
|
||||
|
||||
function getFileName(file, data) {
|
||||
|
||||
const fileNameWithoutExt = stripExt(file);
|
||||
|
||||
// Validate if the file name matches any of the target.RECORD_TYPE values
|
||||
const recordTypes = Object.values(data.target);
|
||||
|
||||
return recordTypes[0].name == fileNameWithoutExt.toLowerCase().split("/")[1];
|
||||
}
|
||||
|
||||
module.exports = getFileName;
|
||||
@@ -1,36 +0,0 @@
|
||||
const fs = require('fs');
|
||||
const { getFileExtension, stripExt } = require('./utils.js');
|
||||
const core = require('@actions/core');
|
||||
|
||||
function getJSON(file) {
|
||||
|
||||
const path = `${process.env.actions_path}/${file}`; // File path.
|
||||
|
||||
const ext = getFileExtension(file);
|
||||
if (path.includes("sub-logs") && !ext || ext != 'json') return 3 //if file is subdomain file but has no ext or diff ext than .json
|
||||
if (!ext) return false; // If no file extension, return.
|
||||
if (ext != 'json') return false; // If file extension is not '.json' return.
|
||||
|
||||
try {
|
||||
if (fs.existsSync(path)) { // Check if file exists in domain directory
|
||||
|
||||
// It exists
|
||||
const rawdata = fs.readFileSync(path); // Read the file
|
||||
const data = JSON.parse(rawdata); // Parse it
|
||||
|
||||
return data; // Return the parsed data if validation passes
|
||||
}
|
||||
return 3; // It doesn't exist
|
||||
} catch(err) {
|
||||
|
||||
core.setOutput('infoMessage', "Could not validate info.");
|
||||
core.setOutput('recordMessage', "Could not validate records.");
|
||||
core.setOutput('jsonData', "Could not read the JSON file, did you have an error in your syntax?")
|
||||
core.setOutput('shouldComment', 'true')
|
||||
console.log(err);
|
||||
return 3;
|
||||
}
|
||||
return 3;
|
||||
}
|
||||
|
||||
module.exports = getJSON;
|
||||
@@ -1,52 +0,0 @@
|
||||
[
|
||||
"*",
|
||||
"_acme-challenge",
|
||||
"_github-challenge-is-a-good-dev",
|
||||
"_github-pages-challenge-is-a-good-dev",
|
||||
"email",
|
||||
"example",
|
||||
"help",
|
||||
"mail",
|
||||
"no-reply",
|
||||
"noreply",
|
||||
"notification",
|
||||
"notifications",
|
||||
"support",
|
||||
"will",
|
||||
"ww",
|
||||
"ww1",
|
||||
"ww2",
|
||||
"ww3",
|
||||
"ww4",
|
||||
"ww5",
|
||||
"ww6",
|
||||
"ww7",
|
||||
"ww8",
|
||||
"ww9",
|
||||
"wwww",
|
||||
"your-domain-name",
|
||||
"www",
|
||||
"docs",
|
||||
"cdn",
|
||||
"dashboard",
|
||||
"create",
|
||||
"documentation",
|
||||
"doc",
|
||||
"content",
|
||||
"network",
|
||||
"shop",
|
||||
"test",
|
||||
"php",
|
||||
"js",
|
||||
"html",
|
||||
"css",
|
||||
"wordpress",
|
||||
"wp",
|
||||
"info",
|
||||
"information",
|
||||
"admin",
|
||||
"administration",
|
||||
"json",
|
||||
"dev",
|
||||
"developer"
|
||||
]
|
||||
@@ -1,74 +0,0 @@
|
||||
const invalidDomains = require('./invalid-domains.json');
|
||||
const fs = require('fs');
|
||||
const core = require('@actions/core');
|
||||
|
||||
function getFiles(path) {
|
||||
// Get all files in path: returns array
|
||||
const allFiles = fs.readdirSync(path);
|
||||
|
||||
return allFiles;
|
||||
}
|
||||
|
||||
function getFileExtension(filename) {
|
||||
// Get file extension
|
||||
return (/[.]/.exec(filename)) ? /[^.]+$/.exec(filename) : undefined;
|
||||
}
|
||||
|
||||
function stripExt(filename) {
|
||||
// Remove file extension
|
||||
return filename.substr(0, filename.lastIndexOf('.'));
|
||||
}
|
||||
|
||||
function checkIfValidIP(str) {
|
||||
// Check if the IP address is valid
|
||||
const regexExp = /^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$/gm;
|
||||
|
||||
return regexExp.test(str);
|
||||
}
|
||||
|
||||
function checkIfValidIPv6(str) {
|
||||
// Insane regex to check if IPv6 address is valid.
|
||||
const regexExp = /^(?:(?:[a-fA-F\d]{1,4}:){7}(?:[a-fA-F\d]{1,4}|:)|(?:[a-fA-F\d]{1,4}:){6}(?:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|:[a-fA-F\d]{1,4}|:)|(?:[a-fA-F\d]{1,4}:){5}(?::(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,2}|:)|(?:[a-fA-F\d]{1,4}:){4}(?:(?::[a-fA-F\d]{1,4}){0,1}:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,3}|:)|(?:[a-fA-F\d]{1,4}:){3}(?:(?::[a-fA-F\d]{1,4}){0,2}:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,4}|:)|(?:[a-fA-F\d]{1,4}:){2}(?:(?::[a-fA-F\d]{1,4}){0,3}:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,5}|:)|(?:[a-fA-F\d]{1,4}:){1}(?:(?::[a-fA-F\d]{1,4}){0,4}:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,6}|:)|(?::(?:(?::[a-fA-F\d]{1,4}){0,5}:(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)(?:\\.(?:25[0-5]|2[0-4]\d|1\d\d|[1-9]\d|\d)){3}|(?::[a-fA-F\d]{1,4}){1,7}|:)))(?:%[0-9a-zA-Z]{1,})?$/gm;
|
||||
|
||||
return regexExp.test(str);
|
||||
}
|
||||
|
||||
function checkIfValidFQDN(str) {
|
||||
// Check if the FQDN is valid
|
||||
const regexExp = /(?=^.{4,253}$)(^((?!-)[a-zA-Z0-9-]{0,62}[a-zA-Z0-9]\.)+[a-zA-Z]{2,63}$)/gi;
|
||||
|
||||
return regexExp.test(str);
|
||||
}
|
||||
|
||||
function checkInvalidDomain(str) {
|
||||
// Check invalid domains
|
||||
if (invalidDomains.includes(str)) {
|
||||
core.setOutput("recordInfo", "This subdomain has been blocked.")
|
||||
return true;
|
||||
}
|
||||
|
||||
// Check reserved domains
|
||||
const files = getFiles("./sub-logs/reserved/").map(file => stripExt(file));
|
||||
|
||||
if (files.includes(str)) {
|
||||
core.setOutput("recordInfo", "This subdomain has been reserved by the is-a-good.dev team.")
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
function isString(value) {
|
||||
return typeof value === 'string' || value instanceof String;
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
checkInvalidDomain,
|
||||
checkIfValidFQDN,
|
||||
checkIfValidIP,
|
||||
checkIfValidIPv6,
|
||||
stripExt,
|
||||
getFileExtension,
|
||||
getFiles,
|
||||
isString
|
||||
}
|
||||
Reference in New Issue
Block a user