Table cannot have a number as name of a column

In a table it is not possible to give the string 0 as the title of a column because it is interpreted as a number instead of the string, passing "0" instead returns the double quotes in the column name.
(yes we need to give the columns the names: 0, 1 , 2, 3 for a particular project)

Below a screenshot as an explanation:

Maybe use an expression binding on the title

toStr(0)

Option 1:
Table header 0
stringFormat returns a string.

Option 2:
Table header 1
ASCII 48 = '0'.

Option 3:
Table header 2
A leading space will force a string.

In general, you cannot have dataset column names that start with a digit. Whether you need it or not. The working approach is to display substitute column headers where needed.

I see there are several workarounds but using an Expressions is not ideal for us because we try to use Python for our Business Logic and using alternate names for the columns means more transformations in the process from the original query.
There's a similar problem for dictionaries associated to a binding which I notified before but hasn't been replied to:

hope these will be properly addressed in the future.

Don't hold your breath waiting for this fundamental behavior to change. You should fix your mis-use of numbers where identifiers are needed, however deep in your technology stack the rot goes.

If you are smart, you will also forbids spaces in such names, along with any other characters that aren't legal in identifiers for programming languages.

If you are wise, you will add automated checks to your development practices to ensure this.

3 Likes

Evil Type Coercion.

Use a language / environment that doesn't do it or do stupid-string-tricks like prepending a non-digit character.

I'm a big fan of strictly typed languages. I've yet to see an easy-to-learn-and-use scripting language that is strictly typed. Probably because strict typing is not easy for many people to wrap their heads around.

I've also yet to see any programming language that didn't have some restrictions on how identifiers are formed.

Do you have a suggestion? Or was that a throw-away line?

My suggestion is

  • understand that in most endeavors there are essentially three approaches - Big Design Up Front (BDUF), Agile, and ad-hoc.
  • understand your personal preferences and the risks (e.g., a large expedition vs an alpine climb)
  • understand the problem that you are trying to solve
  • pick a toolset that best solves the problem
  • implement standards, processes, scripts that mitigate the risks

Ignition solves a certain class of problem very well.
It uses Jython 2.7.
Don't wait for the next release of Jython to fix duck-typing - it isn't going to happen. You don't have to embrace it, but you can accept it.

If you can't accept it then move along. If you are doing HMI/SCADA then you will probably end up writing your own from scratch. And you will discover the stupid-xyz-tricks required there. Once you realize the size of that project it makes it easier to accept the workarounds.

2 Likes

Precisely. Ergo, design practices that mitigate the pain of those workarounds.

I use this when using user input as a key/column name:

import unicodedata

def remove_accents(s):
	# NKFD: https://fr.wikipedia.org/wiki/Normalisation_Unicode#NFKD
	nfkd_form = unicodedata.normalize('NFKD', s)
	return "".join([c for c in nfkd_form if not unicodedata.combining(c)])

class MalformedKeyError(Exception):
	pass

def make_key(s):
	"""
	Sanitize a string so it can be used as a key in an ignition object.
	
	If the first character is a digit, an underscore is added before it
	accents are removed
	leading and trailing whitespaces are removed
	other whitespaces are replaced with an underscore
	"""

	if isinstance(s, str):
		s = s.decode('utf-8')
	key = s.strip()
	if not key:
		raise MalformedKeyError("Can't sanitize {!r} into a valid key".format(s)) 
	if key[0] in "0123456789":
		key = '_' + key
	return re.sub('\W+', '_', remove_accents(key))

And while we're on this subject, I'll take any advice on improving it.
edit: I guess I should filter out any symbols that would make it invalid... like + and such.
edit: changed things a bit to handle any non-alphanum character. This should make it a valid python identifier. Am i forgetting something ?

I generally use the system.dataset.mungeColumnName() function from my Simulation Aids module.

1 Like