class ActiveFacts::Generators::SQL::MYSQL

Generate SQL for MySQL for an ActiveFacts vocabulary. Invoke as

afgen --sql/mysql[=options] <file>.cql

Options are comma or space separated:

Constants

ColumnNameMax
DefaultCharColLength
RESERVED_WORDS

Public Class Methods

new(vocabulary, *options) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 60
def initialize(vocabulary, *options)
  @vocabulary = vocabulary
  @vocabulary = @vocabulary.Vocabulary.values[0] if ActiveFacts::API::Constellation === @vocabulary
  @delay_fks = options.include? "delay_fks"
end

Private Instance Methods

check_clause(column_name, constraints) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 256
def check_clause(column_name, constraints)
  return "" if constraints.empty?
  # REVISIT: Merge all constraints (later; now just use the first)
  " CHECK(" +
    constraints[0].all_allowed_range_sorted.map do |ar|
      vr = ar.value_range
      min = vr.minimum_bound
      max = vr.maximum_bound
      if (min && max && max.value.literal == min.value.literal)
        "#{column_name} = #{sql_value(min.value)}"
      else
        inequalities = [
          min && "#{column_name} >#{min.is_inclusive ? "=" : ""} #{sql_value(min.value)}",
          max && "#{column_name} <#{max.is_inclusive ? "=" : ""} #{sql_value(max.value)}"
        ].compact
        inequalities.size > 1 ? "(" + inequalities*" AND " + ")" : inequalities[0]
      end
    end*" OR " +
  ")"
end
escape(s) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 74
def escape s
  # Escape SQL keywords and non-identifiers
  s = s[0...120]
  if s =~ /[^A-Za-z0-9_]/ || RESERVED_WORDS[s.upcase]
    "`#{s}`"
  else
    s
  end
end
go(s) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 70
def go s
  puts s + ";\n\n"
end
normalise_type(type, length) click to toggle source

Return SQL type and (modified?) length for the passed base type

# File lib/activefacts/generators/sql/mysql.rb, line 85
def normalise_type(type, length)
  sql_type = case type
    when /^Auto ?Counter$/
      'int'

    when /^Signed ?Integer$/,
      /^Signed ?Small ?Integer$/
      s = case
        when length <= 8
          'tinyint'
        when length <= 16
          'shortint'
        when length <= 32
          'int'
        else 'bigint'
        end
      length = nil
      s

    when /^Unsigned ?Integer$/,
      /^Unsigned ?Small ?Integer$/,
      /^Unsigned ?Tiny ?Integer$/
      s = case
        when length <= 8
          'tinyint unsigned'
        when length <= 16
          'shortint unsigned'
        when length <= 32
          'int unsigned'
        else 'bigint'
        end
      length = nil
      s

    when /^Decimal$/
        'decimal'

    when /^Fixed ?Length ?Text$/, /^Char$/
        length ||= DefaultCharColLength
        "char"
    when /^Variable ?Length ?Text$/, /^String$/
        length ||= DefaultCharColLength
        "varchar"
    # There are several large length text types; If you need to store more than 65k chars, look at using MEDIUMTEXT or LONGTEXT
    # CQL does not yet allow you to specify a length for LargeLengthText.
    when /^Large ?Length ?Text$/, /^Text$/
      'text'

    when /^Date ?And ?Time$/, /^Date ?Time$/
      'datetime'
    when /^Date$/
      'date'
    when /^Time$/
      'time'
    when /^Auto ?Time ?Stamp$/
      'timestamp'

    when /^Money$/
      'decimal'
    # Warning: Max 65 kbytes. To use larger types, try MediumBlob (16mb) or LongBlob (4gb)
    when /^Picture ?Raw ?Data$/, /^Image$/
      'blob'
    when /^Variable ?Length ?Raw ?Data$/, /^Blob$/
      'blob'
    # Assuming you only want a boolean out of this. Should we specify length instead?
    when /^BIT$/
      'bit'
    else type # raise "SQL type unknown for standard type #{type}"
    end
  [sql_type, length]
end
puts(s) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 66
def puts s
  @out.puts s
end
sql_string(str) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 252
def sql_string(str)
  "'" + str.gsub(/'/,"''") + "'"
end
sql_value(value) click to toggle source
# File lib/activefacts/generators/sql/mysql.rb, line 248
def sql_value(value)
  value.is_literal_string ? sql_string(value.literal) : value.literal
end