Compare commits

...

27 Commits
v0.2 ... master

Author SHA1 Message Date
5e75be2028 make tests more syntactically conformant
All checks were successful
CMake / build (push) Successful in 50s
2025-09-05 12:51:09 +01:00
ed0b6ed110 refactor, and add proper tests
All checks were successful
CMake / build (push) Successful in 1m1s
2025-09-05 12:43:46 +01:00
a30101f3aa revisions and code cleanup
All checks were successful
CMake / build (push) Successful in 44s
2025-09-05 12:00:39 +01:00
37c156b24a Update .gitea/workflows/cmake.yml
All checks were successful
CMake / build (push) Successful in 19s
2024-07-22 18:54:41 +00:00
e850c6c880 Update .gitea/workflows/cmake.yml
All checks were successful
CMake / build (push) Successful in 24s
2024-07-21 23:39:42 +00:00
25dba8029b Update .gitea/workflows/cmake.yml 2024-07-21 00:17:21 +00:00
7a582b216e add build instructions to the readme 2024-02-23 20:31:03 +00:00
fe2e42a3f2 remove exposing echo 2024-02-22 14:56:17 +00:00
ca206f231d attempt to use LOCIP var 2024-02-22 14:49:27 +00:00
2a781498e7 force etc/hosts for local server 2024-02-22 14:14:34 +00:00
d69279aafd change image name to node16-bullseye to better match what it is 2024-02-22 13:57:49 +00:00
8063e2cd65 Update README.md 2024-02-22 13:35:37 +00:00
541f0aff03 Update .gitea/workflows/cmake.yml 2024-02-22 13:29:10 +00:00
3ff06feb2e Update .gitea/workflows/cmake.yml 2024-02-22 13:27:25 +00:00
255b18e2c5 Update .gitea/workflows/cmake.yml 2024-02-20 18:22:25 +00:00
8cbfd64f2d fixed yaml error 2024-02-20 18:21:36 +00:00
1d890a4593 trying again, but with one runner 2024-02-20 18:19:45 +00:00
51e761df38 make sure build still works 2024-02-20 18:06:35 +00:00
4784a9c5c5 one more time with ubuntu-latest 2024-02-20 17:44:35 +00:00
ec66f74d7d modified build steps 2024-02-20 17:31:27 +00:00
24ee2009b0 modified docker image 2024-02-20 17:21:22 +00:00
e1def09764 try a different docker image 2024-02-20 17:15:45 +00:00
6027c4f1ba change workflow runson 2024-02-15 22:13:13 +00:00
36ed1f9ebc drive a runner action 2024-02-15 22:11:33 +00:00
2d2f392c1e drive a runner action 2024-02-15 21:54:52 +00:00
9ede962190 remove circleci workflow; convert github workflow into gitea workflow 2024-02-15 21:52:54 +00:00
1921f3434d remove circleci workflow; convert github workflow into gitea workflow 2024-02-15 21:52:41 +00:00
9 changed files with 188 additions and 69 deletions

View File

@ -1,13 +0,0 @@
# Use the latest 2.1 version of CircleCI pipeline process engine. See: https://circleci.com/docs/2.0/configuration-reference
version: 2.1
# Use a package of configuration called an orb.
orbs:
# Declare a dependency on the welcome-orb
welcome: circleci/welcome-orb@0.4.1
# Orchestrate or schedule a set of jobs
workflows:
# Name the workflow "welcome"
welcome:
# Run the welcome/run job in its own container
jobs:
- welcome/run

View File

@ -12,11 +12,20 @@ jobs:
# well on Windows or Mac. You can convert this to a matrix build if you need
# cross-platform coverage.
# See: https://docs.github.com/en/free-pro-team@latest/actions/learn-github-actions/managing-complex-workflows#using-a-build-matrix
runs-on: ubuntu-latest
runs-on: ubuntu-gitea
steps:
- name: Prep For Local Builds
run: echo "${LOCIP} gitea.comnenos" >> /etc/hosts
- uses: actions/checkout@v2
- name: Install Build Tools
run: |
apt update
apt -y --no-install-recommends install build-essential clang cmake gdb git wget
- name: Create Build Environment
# Some projects don't allow in-source building, so create a separate build directory
# We'll use this as our working directory for all subsequent commands

View File

@ -1,6 +1,18 @@
cmake_minimum_required(VERSION 3.17)
project(passwdgen)
cmake_minimum_required(VERSION 3.10)
project(passwdgen VERSION 1.0)
set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
add_executable(passwdgen passwdgen.cpp)
# Create a library with the core functionality
add_library(passwdgen_lib passwdgen.cpp)
# Main application
add_executable(passwdgen main.cpp)
target_link_libraries(passwdgen passwdgen_lib)
# Enable testing
enable_testing()
# Add test directory
add_subdirectory(tests)

View File

@ -1,3 +1,38 @@
# passwdgen
### a rudimentary random string password generator
For demo purposes only
## Build
**Bare Bones**
```bash
mkdir build
g++ -o build/passwdgen ./passwdgen.cpp
```
**From CMAKE**
```bash
mkdir build
cd build
cmake ..
make
```
Then, just copy the compiled binary to somewhere on your $PATH
## Testing
To run the tests:
```bash
mkdir build
cd build
cmake ..
make
ctest
```
or directly:
```bash
./tests/passwdgen_test
```

46
main.cpp Normal file
View File

@ -0,0 +1,46 @@
//
// Created by gmgauthier on 05/09/25.
//
// main.cpp
#include "passwdgen.h"
#include <iostream>
#include <string>
int main(int argc, char *argv[]) {
int passwordLength = 0;
bool punc = false;
if (argc < 1) {
std::cout << random_string(32, false) << std::endl;
return 0;
}
for (int i = 1; i < argc; ++i) {
std::string arg = argv[i];
if ((arg == "-h") || (arg == "--help")) {
show_usage(argv[0]);
return 0;
}
if (arg == "-p") {
punc = true;
} else if ((arg == "-l") || (arg == "--length")) {
if (not argv[i +1]) {
std::cerr << "Specify a password length" << std::endl;
return 1;
}
std::string passwordLengthStr = argv[i + 1];
try {
passwordLength = std::stoi(passwordLengthStr);
} catch ([[maybe_unused]] const std::invalid_argument& e){
std::cerr << "Length must be a valid integer" << std::endl;
return 1;
}
}
}
if (passwordLength == 0) {
passwordLength = 32;
}
std::string password = random_string(passwordLength, punc);
std::cout << password << std::endl;
return 0;
}

View File

@ -1,25 +1,22 @@
//
// passwdgen.cpp
// Created by Greg Gauthier on 2020.10.22.
//
// passwdgen.cpp
#include "passwdgen.h"
#include <iostream>
#include <random>
std::string random_string(std::size_t length, bool punc) {
std::string CHARACTERS;
std::string ALPHANUM = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
std::string SPECIALS = "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~";
const std::string SPECIALS = "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~";
if (punc) {
CHARACTERS = ALPHANUM.append(SPECIALS);
} else {
CHARACTERS = ALPHANUM;
}
std::random_device random_device;
std::mt19937 generator(random_device());
std::uniform_int_distribution<> distribution(0.0, CHARACTERS.size() - 1.0);
std::uniform_int_distribution<> distribution(0, static_cast<int>(CHARACTERS.size() - 1));
std::string random_string;
for (std::size_t i = 0; i < length; ++i) {
@ -28,53 +25,11 @@ std::string random_string(std::size_t length, bool punc) {
return random_string;
}
void show_usage(std::string binname) {
std::cerr << "Usage: " << binname << " [OPTIONS] " << std::endl
void show_usage(const std::string& name) {
std::cerr << "Usage: " << name << " [OPTIONS] " << std::endl
<< "Options:" << std::endl
<< "\t-h, --help \t\tShow this help message" << std::endl
<< "\t-l, --length [n] \t\tThe length of the password (default: 32)" << std::endl
<< "\t-p, --punctuation \t\tToggle special characters (default: false)"
<< std::endl;
}
int main(int argc, char *argv[]) {
std::string passlenstr;
int passlen = 0;
bool punc = false;
if (argc < 1) {
std::cout << random_string(32, false) << std::endl;
return 0;
} else {
for (int i = 1; i < argc; ++i) {
std::string arg = argv[i];
if ((arg == "-h") || (arg == "--help")) {
show_usage(argv[0]);
return 0;
} else if (arg == "-p") {
punc = true;
} else if ((arg == "-l") || (arg == "--length")) {
if (not argv[i +1]) {
std::cerr << "Specify a password length" << std::endl;
return 1;
} else {
passlenstr = argv[i + 1];
try {
passlen = std::stoi(passlenstr);
} catch (const std::invalid_argument& e){
std::cerr << "Length must be a valid integer" << std::endl;
return 1;
}
}
}
}
if (passlen == 0) {
passlen = 32;
}
std::string password = random_string(passlen, punc);
std::cout << password << std::endl;
return 0;
}
}

10
passwdgen.h Normal file
View File

@ -0,0 +1,10 @@
// passwdgen.h
#pragma once
#include <string>
// Core password generation functionality
std::string random_string(std::size_t length, bool punc);
// Help message display
void show_usage(const std::string& name);

17
tests/CMakeLists.txt Normal file
View File

@ -0,0 +1,17 @@
# tests/CMakeLists.txt
add_executable(passwdgen_test passwdgen_test.cpp)
# Link against the library that contains the functions we want to test
target_link_libraries(passwdgen_test passwdgen_lib)
# Register the test with CTest
add_test(
NAME passwdgen_tests
COMMAND passwdgen_test
)
# Define what it means for the test to pass
set_tests_properties(passwdgen_tests
PROPERTIES PASS_REGULAR_EXPRESSION "All tests passed!"
)

48
tests/passwdgen_test.cpp Normal file
View File

@ -0,0 +1,48 @@
// tests/passwdgen_test.cpp
#include "../passwdgen.h"
#include <iostream>
#include <regex>
#include <cassert>
void test_random_string_length() {
for (const int lengths[] = {0, 1, 10, 32, 100}; const auto length : lengths) {
std::string result = random_string(length, false);
assert(result.length() == length);
std::string result_with_punc = random_string(length, true);
assert(result_with_punc.length() == length);
}
std::cout << "Length test passed\n";
}
void test_alphanumeric_only() {
const std::regex alphanumeric_only("^[a-zA-Z0-9]*$");
for (int i = 0; i < 10; i++) {
std::string result = random_string(20, false);
assert(std::regex_match(result, alphanumeric_only));
}
std::cout << "Alphanumeric test passed\n";
}
void test_with_punctuation() {
bool found_special = false;
for (int i = 0; i < 100 && !found_special; i++) {
std::string result = random_string(100, true);
if (!std::regex_match(result, std::regex("^[a-zA-Z0-9]*$"))) {
found_special = true;
}
}
assert(found_special);
std::cout << "Punctuation test passed\n";
}
int main() {
test_random_string_length();
test_alphanumeric_only();
test_with_punctuation();
std::cout << "All tests passed!\n";
return 0;
}