This utility will hopefully save you many hours of tedious coding by writing lots of code for you,
in whatever language you want, in whatever style you're used to. IDEs help out quite a bit when
writing you code, using auto-complete, suggestions, inserting blocks of code for you. But it
still takes a lot of time to write. Using this utility will speed up the brainstorming and
maintenance quite a bit, if used right.
Using a simple text editor you can quickly brainstorm your objects, properties, relationships and
have the code auto-generate as you go. As you refine your project, your code gets rewritten with
more details. You can have your brainstorm converted into multiple languages at once
(Java, SQL, PHP, etc).
Note: It's mainly used for managing your project ORM needs.
Download the spooky-coder.jar file and put it where you store your awesome utilities.
First you'll need to create your brainstorm text file (see the Brainstorm Format below).
user
first
last
int age
$ java -jar spooky-coder.jar -i schema.brain -o java,sql
Success.
Syntax: Spooky <-i|--in [type]:<file>> [-o|--out <output types>] [-d|--outdir <directory>] [-D|--debug] [-l|--libdir <lib dir>] [-c|--conf <config file>] [-h|--help]
-i [type]:<file> input type and file to convert from (default is brainstorm:schema.brain)
-o <type>, ... one or more output types to convert to (default is java)
-c <config> config file containing customizations
-d <dir> directory where output files will be written to (default is src)
-a show all converters and their customization parameters
-D debug mode
-l <lib dir> directory where conversion classes are found (default is lib)
-h display this help message
This is a quick and dirty format that allows you to define very simple class names and properties
and have usable code written immediately. Your code gets rewritten as you add more and more
detail to your brainstorm.
There are very few rules when creating a brainstorm:
Assumptions
If no property modifier is specified, string is the default type. Ids are automatically
create for each object, using the object name and appending id on the end (ie, userId).
The property name and modifiers can be placed wherever you want them. For example a username
field can be any of the following:
Example:
user
first
last
name
age
address
Will create a User table with those columns as strings, as well as working, well-written java,
php, perl, python, C++, code. Now you add more data:
user
first required
last
name
int age
address address required
address
street required
street2
city required
state required
zip
Now you want to add a username, and make sure it's always unique, and make sure the
state property is two characters. Let's add a creation datetime as well.
user
first required
created datetime required
username unique required
last
name
int age
address address required
address
street required
street2
city required
state(2) required
zip
The ids are automatically generated for each object (a User class will get userId as the id). If you want to specify your own id, use the id (primary, or primary key) flag.
Note: You can change the var.style parameter to be like userid, USERID, userId, user_id, UserId, etc. See the Styles section below.
user
id personId
first
last
There are the property types you can specify, that are pretty much recognized in any language.
boolean, bool, bit
byte
char
datetime, timedate, date_time, time_date
date
time
timestamp
float, decimal, number
integer, int
long
string, str, text, varchar
enum, list
bit, flags
money, currency
blob
Enums are common in most languages and are easy to create. You can assign a number to each option, or accept the default.
This example will create a Role enum with the specified values:
user
username required
enum(root, admin, user, guest) role
Java:
public enum Role {
ROOT,
ADMIN,
USER,
GUEST
};
Using values:
user
username required
enum(root = 1001, admin = 2002, user, guest = 4004) role
Java:
public enum Role {
ROOT = 1001,
ADMIN = 2002,
USER,
GUEST = 4004
};
Bit flags aren't nearly as common as enums, but useful for when using several booleans into one value, like read, write, execute in permissions.
Example:
user
username required
flags(read, write, execute, delete) permissions
Java:
public final int PERMISSIONS_READ = 1;
public final int PERMISSIONS_WRITE = 2;
public final int PERMISSIONS_EXECUTE = 4;
public final int PERMISSIONS_DELETE = 8;
Just like enums, you can assign integer values to the flags.
user
username required
flags(read, write, exec_del = 12) permissions
Java:
public final int PERMISSIONS_READ = 1;
public final int PERMISSIONS_WRITE = 2;
public final int PERMISSIONS_EXEC_DELETE = 12;
By referencing another object by name you create a one-to-one relationship. You can also use the one_to_one keyword.
user
first
address address <--- one-to-one
address
street
city
state
zip
Use brackets [] to denote a one-to-many relationship between objects. You can also use the one_to_many keyword, array, -<, or 1*.
User
first
address[] address <---- one User to many address objects (you can also say address address[])
address
street
city
state
zip
Use angle brackets <> to denote many-to-many relationship between objects. You can also use the many_to_many keyword.
User
first
address<> address <---- many User objects to many address objects (you can also say address address<>)
address
street
city
state
zip
Intersect Table:
If you are using SQL, you know that you'll need an intersect table to be able to work with many-to-many relationships. By default a UserAddress table is created for you with the userId and addressId.
If you want to use a different name, specify it inbetween the angle brackets <>. For example:
address<MyUserAddresses> address
Here are additional property types you can add to change the way code is generated:
Name | Description |
---|---|
unique | For SQL, it will mark the column as UNIQUE |
required, not_null | For SQL, it will mark the column as NOT NULL |
readonly, ro | Will not create a setter method |
writeonly, wo | Will not create a getter method |
hidden | No setters or getters will be created |
User
username required unique <--- SQL will have UNIQUE NOT NULL
first required <--- SQL will have NOT NULL
last required <--- SQL will have NOT NULL
password writeonly <--- make sure no getter is created
By default a string is 50 characters wide, when it needs to be specified (SQL). You can change this by adding the length and precision in parenthesis, like in SQL.
User
first(25)
last(200)
float(4,2) <-- or just use money shortcut
You can tweak several styles to customize the code. You know what I mean. Make it look like you wrote it all. Create a file called brainstorm.config (or use -c to point to somewhere else). Here are styles you can adjust:
Types:
Style | Type | Default | Description |
---|---|---|---|
class.style | style | title | Class name style |
method.style | style | camel | Method style |
var.style | style | camel | Variable style |
use.tabs | bool | true | Use tabs instead of spaces if true |
num.spaces | int | 4 | Number of spaces to use if use.tabs is false |
table.style | style | title | db-specific table style |
column.style | style | camel | db-specific column style |
use.persist | bool | true | Write Java persistence code |
align.class.braces | bool | false | Align class braces |
align.method.braces | bool | false | Align method braces |