ruby-xslt 0.9.2
Sign up to get free protection for your applications and to get access to all the features.
- data/AUTHORS +23 -0
- data/COPYING +340 -0
- data/ChangeLog +64 -0
- data/README +137 -0
- data/debug/memwatch.c +2664 -0
- data/debug/memwatch.h +707 -0
- data/examples/commentary.dtd +34 -0
- data/examples/functions.xsl +51 -0
- data/examples/fuzface.rb +13 -0
- data/examples/fuzface.xml +154 -0
- data/examples/fuzface.xsl +4 -0
- data/examples/fuzface_REXML.rb +11 -0
- data/examples/fuzface_XML-Simple.rb +12 -0
- data/examples/fuzface_data.rb +13 -0
- data/examples/fuzface_error.rb +86 -0
- data/examples/fuzface_to_s.rb +9 -0
- data/examples/info.rb +19 -0
- data/examples/ramblings.xsl +46 -0
- data/examples/test.xml +5 -0
- data/examples/test.xsl +18 -0
- data/examples/test_functions.rb +18 -0
- data/examples/test_parameters.rb +13 -0
- data/extconf.rb +114 -0
- data/extfunc.c +216 -0
- data/extfunc.h +26 -0
- data/parameters.c +59 -0
- data/parameters.h +20 -0
- data/parser.c +228 -0
- data/parser.h +30 -0
- data/rb_utils.c +30 -0
- data/rb_utils.h +34 -0
- data/ruby-xslt.gemspec +19 -0
- data/tests/t.xml +2 -0
- data/tests/t.xsl +6 -0
- data/tests/test.rb +125 -0
- data/xslt.c +619 -0
- data/xslt.h +98 -0
- metadata +98 -0
data/examples/test.xml
ADDED
data/examples/test.xsl
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
<?xml version="1.0" encoding="ISO-8859-1"?>
|
2
|
+
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
|
3
|
+
<xsl:output method="text" encoding="iso-8859-1" indent="no"/>
|
4
|
+
<xsl:param name="p1"/>
|
5
|
+
<xsl:param name="p2"/>
|
6
|
+
|
7
|
+
<xsl:template match="/">
|
8
|
+
p1:<xsl:value-of select="$p1"/>
|
9
|
+
p2:<xsl:value-of select="$p2"/>
|
10
|
+
<xsl:apply-templates/>
|
11
|
+
</xsl:template>
|
12
|
+
|
13
|
+
<xsl:template match="node">
|
14
|
+
<xsl:value-of select="."/>(<xsl:value-of select="@number"/>)
|
15
|
+
</xsl:template>
|
16
|
+
|
17
|
+
</xsl:stylesheet>
|
18
|
+
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require "../xslt"
|
2
|
+
|
3
|
+
class XML::XSLT
|
4
|
+
def round_trip( arg )
|
5
|
+
arg
|
6
|
+
end
|
7
|
+
def type( arg )
|
8
|
+
arg.class.to_s
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
xslt = XML::XSLT.new()
|
13
|
+
xslt.xsl = "functions.xsl"
|
14
|
+
xslt.xml = "test.xml"
|
15
|
+
XML::XSLT.extFunction("round-trip", "http://test.none", xslt)
|
16
|
+
XML::XSLT.extFunction("type", "http://test.none", xslt)
|
17
|
+
|
18
|
+
puts xslt.serve
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require "../xslt"
|
2
|
+
|
3
|
+
xslt = XML::XSLT.new()
|
4
|
+
xslt.xsl = "test.xsl"
|
5
|
+
xslt.xml = "test.xml"
|
6
|
+
xslt.parameters = { "p1" => "the first parameter ...",
|
7
|
+
"p2" => "'and the second one!'" }
|
8
|
+
#xslt.save("test.html")
|
9
|
+
puts xslt.serve
|
10
|
+
xslt.parameters = { "p1" => "Ruby...",
|
11
|
+
"p2" => "'...is cool !'" }
|
12
|
+
#xslt.save("test.html")
|
13
|
+
puts xslt.serve
|
data/extconf.rb
ADDED
@@ -0,0 +1,114 @@
|
|
1
|
+
#!/usr/bin/ruby -w
|
2
|
+
# See the LICENSE file for copyright and distribution information
|
3
|
+
|
4
|
+
require "mkmf"
|
5
|
+
|
6
|
+
def help
|
7
|
+
print <<HELP
|
8
|
+
"extconf.rb" configures this package to adapt to many kinds of systems.
|
9
|
+
|
10
|
+
Usage: ruby extconf.rb [OPTION]...
|
11
|
+
|
12
|
+
Configuration:
|
13
|
+
--help display this help and exit
|
14
|
+
|
15
|
+
--with-xslt-lib=PATH
|
16
|
+
--with-xslt-include=PATH
|
17
|
+
--with-xslt-dir=PATH specify the directory name for the libxslt include
|
18
|
+
files and/or library
|
19
|
+
|
20
|
+
--enable-error-handler enables a VERY crude error handler. Error messages
|
21
|
+
are appended to the class variable XML::XSLT and can
|
22
|
+
be accessed with the class method XML::XSLT.errors
|
23
|
+
(will change in a future version)
|
24
|
+
--disable-exslt disables libexslt support <http://exslt.org/>
|
25
|
+
|
26
|
+
--enable-debug compile with memwatch
|
27
|
+
<http://www.linkdata.se/sourcecode.html>
|
28
|
+
|
29
|
+
HELP
|
30
|
+
end
|
31
|
+
|
32
|
+
if ARGV.include?( "--help" )
|
33
|
+
help()
|
34
|
+
exit 0
|
35
|
+
end
|
36
|
+
|
37
|
+
if enable_config("debug", false)
|
38
|
+
File.symlink( "debug/memwatch.h", "memwatch.h" ) if( ! File.exist?("memwatch.h") )
|
39
|
+
File.symlink( "debug/memwatch.c", "memwatch.c" ) if( ! File.exist?("memwatch.c") )
|
40
|
+
$CFLAGS += " -DMEMWATCH -D__DEBUG__"
|
41
|
+
end
|
42
|
+
|
43
|
+
if enable_config("error-handler", false)
|
44
|
+
$CFLAGS += " -DUSE_ERROR_HANDLER"
|
45
|
+
end
|
46
|
+
|
47
|
+
$LIBPATH.push(Config::CONFIG['libdir'])
|
48
|
+
|
49
|
+
def crash(str)
|
50
|
+
printf(" extconf failure: %s\n", str)
|
51
|
+
exit 1
|
52
|
+
end
|
53
|
+
|
54
|
+
#unless have_library("z", "inflate")
|
55
|
+
# crash("need zlib")
|
56
|
+
#else
|
57
|
+
# $defs.push('-DHAVE_ZLIB_H')
|
58
|
+
#end
|
59
|
+
|
60
|
+
if dir_config( "xslt" ) != [nil, nil]
|
61
|
+
inc, lib = dir_config( 'xslt' )
|
62
|
+
$LDFLAGS << " -L#{lib} -lxslt -lxml2 -lz -lpthread -liconv -lm"
|
63
|
+
$CFLAGS << " -I#{inc}"
|
64
|
+
elsif ex = find_executable( "xslt-config" )
|
65
|
+
$LDFLAGS << ' ' + `#{ex} --libs`.chomp
|
66
|
+
$CFLAGS << ' ' + `#{ex} --cflags`.chomp
|
67
|
+
else
|
68
|
+
crash(<<EOL)
|
69
|
+
need libxslt.
|
70
|
+
|
71
|
+
Install the library or try one of the following options to extconf.rb:
|
72
|
+
|
73
|
+
--with-xslt-lib=/path/to/libxslt/lib
|
74
|
+
--with-xslt-include=/path/to/libxslt/include
|
75
|
+
EOL
|
76
|
+
end
|
77
|
+
|
78
|
+
if enable_config("exslt", true)
|
79
|
+
$LDFLAGS << " -lexslt"
|
80
|
+
$CFLAGS += " -DUSE_EXSLT"
|
81
|
+
end
|
82
|
+
|
83
|
+
$CFLAGS = '-g -Wall ' + $CFLAGS
|
84
|
+
|
85
|
+
puts "compile with : "
|
86
|
+
puts " CFLAGS = #{$CFLAGS}"
|
87
|
+
puts " LDFLAGS = #{$LDFLAGS}"
|
88
|
+
puts
|
89
|
+
|
90
|
+
create_header()
|
91
|
+
create_makefile("xml/xslt")
|
92
|
+
|
93
|
+
###### Modify Makefile: #######
|
94
|
+
File.rename( "Makefile", "Makefile.orig" )
|
95
|
+
oldmkfl = File.open( "Makefile.orig" )
|
96
|
+
newmkfl = File.open( "Makefile", "w" )
|
97
|
+
oldmkfl.each_line{ |line|
|
98
|
+
case(line)
|
99
|
+
when /^all:/
|
100
|
+
newmkfl.puts(line)
|
101
|
+
newmkfl.puts("")
|
102
|
+
newmkfl.puts("test: all") # insert the "test" target
|
103
|
+
newmkfl.puts("\t\t@cd tests && ruby test.rb && cd ..")
|
104
|
+
newmkfl.puts("doc: all") # insert the "doc" target
|
105
|
+
newmkfl.puts("\t\t@rdoc -S -t \"Ruby/XSLT Documentation\" README AUTHORS ChangeLog xslt.c")
|
106
|
+
when /^distclean:/
|
107
|
+
newmkfl.puts(line)
|
108
|
+
newmkfl.puts("\t\t@-$(RM) memwatch.h memwatch.c Makefile.orig")
|
109
|
+
newmkfl.puts("\t\t@-$(RM)r doc")
|
110
|
+
else
|
111
|
+
newmkfl.puts(line)
|
112
|
+
end
|
113
|
+
}
|
114
|
+
newmkfl.close
|
data/extfunc.c
ADDED
@@ -0,0 +1,216 @@
|
|
1
|
+
/**
|
2
|
+
* Copyright (C) 2005 Gregoire Lejeune <gregoire.lejeune@free.fr>
|
3
|
+
*
|
4
|
+
* This program is free software; you can redistribute it and/or modify
|
5
|
+
* it under the terms of the GNU General Public License as published by
|
6
|
+
* the Free Software Foundation; either version 2 of the License, or
|
7
|
+
* (at your option) any later version.
|
8
|
+
*
|
9
|
+
* This program is distributed in the hope that it will be useful,
|
10
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
11
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
12
|
+
* GNU General Public License for more details.
|
13
|
+
*
|
14
|
+
* You should have received a copy of the GNU General Public License
|
15
|
+
* along with this program; if not, write to the Free Software
|
16
|
+
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "xslt.h"
|
20
|
+
|
21
|
+
extern VALUE mXML;
|
22
|
+
extern VALUE cXSLT;
|
23
|
+
|
24
|
+
/**
|
25
|
+
* external function support, patch from :
|
26
|
+
*
|
27
|
+
* Brendan Taylor
|
28
|
+
* whateley@gmail.com
|
29
|
+
*
|
30
|
+
*/
|
31
|
+
|
32
|
+
|
33
|
+
/* converts an xmlXPathObjectPtr to a Ruby VALUE
|
34
|
+
* number -> float
|
35
|
+
* boolean -> boolean
|
36
|
+
* string -> string
|
37
|
+
* nodeset -> an array of REXML::Elements
|
38
|
+
*/
|
39
|
+
VALUE xpathObj2value(xmlXPathObjectPtr obj, xmlDocPtr doc)
|
40
|
+
{
|
41
|
+
VALUE ret = Qnil;
|
42
|
+
|
43
|
+
if (obj == NULL) {
|
44
|
+
return ret;
|
45
|
+
}
|
46
|
+
|
47
|
+
switch (obj->type) {
|
48
|
+
case XPATH_NODESET:
|
49
|
+
rb_require("rexml/document");
|
50
|
+
ret = rb_ary_new();
|
51
|
+
|
52
|
+
if ((obj->nodesetval != NULL) && (obj->nodesetval->nodeNr != 0)) {
|
53
|
+
xmlBufferPtr buff = xmlBufferCreate();
|
54
|
+
xmlNodePtr node;
|
55
|
+
int i;
|
56
|
+
|
57
|
+
// this assumes all the nodes are elements, which is a bad idea
|
58
|
+
for (i = 0; i < obj->nodesetval->nodeNr; i++) {
|
59
|
+
node = obj->nodesetval->nodeTab[i];
|
60
|
+
|
61
|
+
if( node->type == XML_ELEMENT_NODE ) {
|
62
|
+
xmlNodeDump(buff, doc, node, 0, 0);
|
63
|
+
|
64
|
+
VALUE cREXML = rb_const_get(rb_cObject, rb_intern("REXML"));
|
65
|
+
VALUE cDocument = rb_const_get(cREXML, rb_intern("Document"));
|
66
|
+
VALUE rDocument = rb_funcall(cDocument, rb_intern("new"), 1,rb_str_new2((char *)buff->content));
|
67
|
+
VALUE rElement = rb_funcall(rDocument, rb_intern("root"), 0);
|
68
|
+
|
69
|
+
rb_ary_push(ret, rElement);
|
70
|
+
|
71
|
+
// empty the buffer (xmlNodeDump appends rather than replaces)
|
72
|
+
xmlBufferEmpty(buff);
|
73
|
+
} else if ( node->type == XML_TEXT_NODE ) {
|
74
|
+
rb_ary_push(ret, rb_str_new2((char *)node->content));
|
75
|
+
}
|
76
|
+
}
|
77
|
+
xmlBufferFree(buff);
|
78
|
+
}
|
79
|
+
break;
|
80
|
+
case XPATH_BOOLEAN:
|
81
|
+
ret = obj->boolval ? Qtrue : Qfalse;
|
82
|
+
break;
|
83
|
+
case XPATH_NUMBER:
|
84
|
+
ret = rb_float_new(obj->floatval);
|
85
|
+
break;
|
86
|
+
case XPATH_STRING:
|
87
|
+
ret = rb_str_new2((char *) obj->stringval);
|
88
|
+
break;
|
89
|
+
/* these cases were in libxslt's python bindings, but i don't know what they are, so i'll leave them alone */
|
90
|
+
case XPATH_XSLT_TREE:
|
91
|
+
case XPATH_POINT:
|
92
|
+
case XPATH_RANGE:
|
93
|
+
case XPATH_LOCATIONSET:
|
94
|
+
default:
|
95
|
+
rb_warning("xpathObj2value: can't convert XPath object type %d to Ruby object\n", obj->type );
|
96
|
+
}
|
97
|
+
xmlXPathFreeObject(obj);
|
98
|
+
return ret;
|
99
|
+
}
|
100
|
+
|
101
|
+
/*
|
102
|
+
* converts a Ruby VALUE to an xmlXPathObjectPtr
|
103
|
+
* boolean -> boolean
|
104
|
+
* number -> number
|
105
|
+
* string -> escaped string
|
106
|
+
* array -> array of parsed nodes
|
107
|
+
*/
|
108
|
+
xmlXPathObjectPtr value2xpathObj (VALUE val) {
|
109
|
+
xmlXPathObjectPtr ret = NULL;
|
110
|
+
|
111
|
+
switch (TYPE(val)) {
|
112
|
+
case T_TRUE:
|
113
|
+
case T_FALSE:
|
114
|
+
ret = xmlXPathNewBoolean(RTEST(val));
|
115
|
+
break;
|
116
|
+
case T_FIXNUM:
|
117
|
+
case T_FLOAT:
|
118
|
+
ret = xmlXPathNewFloat(NUM2DBL(val));
|
119
|
+
break;
|
120
|
+
case T_STRING:
|
121
|
+
{
|
122
|
+
xmlChar *str;
|
123
|
+
|
124
|
+
// we need the Strdup (this is the major bugfix for 0.8.1)
|
125
|
+
str = xmlStrdup((const xmlChar *) STR2CSTR(val));
|
126
|
+
ret = xmlXPathWrapString(str);
|
127
|
+
}
|
128
|
+
break;
|
129
|
+
case T_NIL:
|
130
|
+
ret = xmlXPathNewNodeSet(NULL);
|
131
|
+
break;
|
132
|
+
case T_ARRAY: {
|
133
|
+
int i,j;
|
134
|
+
ret = xmlXPathNewNodeSet(NULL);
|
135
|
+
|
136
|
+
for(i = RARRAY(val)->len; i > 0; i--) {
|
137
|
+
xmlXPathObjectPtr obj = value2xpathObj( rb_ary_shift( val ) );
|
138
|
+
if ((obj->nodesetval != NULL) && (obj->nodesetval->nodeNr != 0)) {
|
139
|
+
for(j = 0; j < obj->nodesetval->nodeNr; j++) {
|
140
|
+
xmlXPathNodeSetAdd( ret->nodesetval, obj->nodesetval->nodeTab[j] );
|
141
|
+
}
|
142
|
+
}
|
143
|
+
}
|
144
|
+
break; }
|
145
|
+
case T_DATA:
|
146
|
+
case T_OBJECT: {
|
147
|
+
if( strcmp( getRubyObjectName( val ), "REXML::Document" ) == 0 || strcmp(getRubyObjectName( val ), "REXML::Element") == 0 ) {
|
148
|
+
|
149
|
+
VALUE to_s = rb_funcall( val, rb_intern( "to_s" ), 0 );
|
150
|
+
xmlDocPtr doc = xmlParseDoc((xmlChar *) STR2CSTR(to_s));
|
151
|
+
|
152
|
+
ret = xmlXPathNewNodeSet((xmlNode *)doc->children);
|
153
|
+
break;
|
154
|
+
} else if( strcmp( getRubyObjectName( val ), "REXML::Text" ) == 0 ) {
|
155
|
+
VALUE to_s = rb_funcall( val, rb_intern( "to_s" ), 0 );
|
156
|
+
|
157
|
+
xmlChar *str;
|
158
|
+
|
159
|
+
str = xmlStrdup((const xmlChar *) STR2CSTR(to_s));
|
160
|
+
ret = xmlXPathWrapString(str);
|
161
|
+
break;
|
162
|
+
}
|
163
|
+
// this drops through so i can reuse the error message
|
164
|
+
}
|
165
|
+
default:
|
166
|
+
rb_warning( "value2xpathObj: can't convert class %s to XPath object\n", getRubyObjectName(val));
|
167
|
+
return NULL;
|
168
|
+
}
|
169
|
+
|
170
|
+
return ret;
|
171
|
+
}
|
172
|
+
|
173
|
+
/*
|
174
|
+
* chooses what registered function to call and calls it
|
175
|
+
*/
|
176
|
+
void xmlXPathFuncCallback( xmlXPathParserContextPtr ctxt, int nargs) {
|
177
|
+
VALUE result, arguments[nargs];
|
178
|
+
VALUE ns_hash, func_hash, object;
|
179
|
+
const xmlChar *namespace;
|
180
|
+
char *rb_func, *chr;
|
181
|
+
xmlXPathObjectPtr obj;
|
182
|
+
int i;
|
183
|
+
|
184
|
+
if (ctxt == NULL || ctxt->context == NULL)
|
185
|
+
return;
|
186
|
+
|
187
|
+
rb_func = strdup((char *)ctxt->context->function);
|
188
|
+
namespace = ctxt->context->functionURI;
|
189
|
+
|
190
|
+
ns_hash = rb_cvar_get(cXSLT, rb_intern("@@extFunctions"));
|
191
|
+
|
192
|
+
func_hash = rb_hash_aref(ns_hash, rb_str_new2((char *)namespace));
|
193
|
+
|
194
|
+
if(func_hash == Qnil) {
|
195
|
+
rb_warning( "xmlXPathFuncCallback: namespace %s not found!\n", namespace );
|
196
|
+
}
|
197
|
+
|
198
|
+
object = rb_hash_aref(func_hash, rb_str_new2((char *)rb_func));
|
199
|
+
|
200
|
+
for (i = nargs - 1; i >= 0; i--) {
|
201
|
+
obj = valuePop(ctxt);
|
202
|
+
arguments[i] = xpathObj2value(obj, ctxt->context->doc);
|
203
|
+
}
|
204
|
+
|
205
|
+
/* -s are common in XSLT function names, but illegal for Ruby method names */
|
206
|
+
while( (chr = strchr(rb_func, '-')) != NULL ) {
|
207
|
+
chr[0] = '_'; /* so we pretend the - was a _ all along */
|
208
|
+
}
|
209
|
+
|
210
|
+
result = rb_funcall2( object, rb_intern(rb_func), nargs, arguments);
|
211
|
+
|
212
|
+
free( rb_func );
|
213
|
+
|
214
|
+
obj = value2xpathObj(result);
|
215
|
+
valuePush(ctxt, obj);
|
216
|
+
}
|
data/extfunc.h
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
/**
|
2
|
+
* Copyright (C) 2005 Gregoire Lejeune <gregoire.lejeune@free.fr>
|
3
|
+
*
|
4
|
+
* This program is free software; you can redistribute it and/or modify
|
5
|
+
* it under the terms of the GNU General Public License as published by
|
6
|
+
* the Free Software Foundation; either version 2 of the License, or
|
7
|
+
* (at your option) any later version.
|
8
|
+
*
|
9
|
+
* This program is distributed in the hope that it will be useful,
|
10
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
11
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
12
|
+
* GNU General Public License for more details.
|
13
|
+
*
|
14
|
+
* You should have received a copy of the GNU General Public License
|
15
|
+
* along with this program; if not, write to the Free Software
|
16
|
+
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "xslt.h"
|
20
|
+
|
21
|
+
#include <libxml/xpathInternals.h>
|
22
|
+
#include <libxslt/extensions.h>
|
23
|
+
|
24
|
+
VALUE xpathObj2value( xmlXPathObjectPtr, xmlDocPtr );
|
25
|
+
xmlXPathObjectPtr value2xpathObj( VALUE );
|
26
|
+
void xmlXPathFuncCallback( xmlXPathParserContextPtr, int );
|
data/parameters.c
ADDED
@@ -0,0 +1,59 @@
|
|
1
|
+
/**
|
2
|
+
* Copyright (C) 2005 Gregoire Lejeune <gregoire.lejeune@free.fr>
|
3
|
+
*
|
4
|
+
* This program is free software; you can redistribute it and/or modify
|
5
|
+
* it under the terms of the GNU General Public License as published by
|
6
|
+
* the Free Software Foundation; either version 2 of the License, or
|
7
|
+
* (at your option) any later version.
|
8
|
+
*
|
9
|
+
* This program is distributed in the hope that it will be useful,
|
10
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
11
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
12
|
+
* GNU General Public License for more details.
|
13
|
+
*
|
14
|
+
* You should have received a copy of the GNU General Public License
|
15
|
+
* along with this program; if not, write to the Free Software
|
16
|
+
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "xslt.h"
|
20
|
+
|
21
|
+
/**
|
22
|
+
* parameters support, patch from :
|
23
|
+
*
|
24
|
+
* Eust�quio "TaQ" Rangel
|
25
|
+
* eustaquiorangel@yahoo.com
|
26
|
+
* http://beam.to/taq
|
27
|
+
*
|
28
|
+
*/
|
29
|
+
VALUE each_pair( VALUE obj ) {
|
30
|
+
return rb_funcall( obj, rb_intern("each"), 0, 0 );
|
31
|
+
}
|
32
|
+
|
33
|
+
VALUE process_pair( VALUE pair, VALUE rbparams ) {
|
34
|
+
VALUE key, value;
|
35
|
+
// Thx to alex__
|
36
|
+
int count = FIX2INT( rb_funcall( rbparams, rb_intern("size"), 0, 0 ) );
|
37
|
+
// static int count = 0;
|
38
|
+
char *xValue = NULL;
|
39
|
+
|
40
|
+
Check_Type( pair, T_ARRAY );
|
41
|
+
|
42
|
+
key = RARRAY(pair)->ptr[0];
|
43
|
+
value = RARRAY(pair)->ptr[1];
|
44
|
+
|
45
|
+
Check_Type( key, T_STRING );
|
46
|
+
Check_Type( value, T_STRING );
|
47
|
+
|
48
|
+
xValue = STR2CSTR( value );
|
49
|
+
if( xValue[0] != '\'' && xValue[strlen( xValue ) - 1] != '\'' ) {
|
50
|
+
value = rb_str_concat( value, rb_str_new2( "'" ) );
|
51
|
+
value = rb_str_concat( rb_str_new2( "'" ), value );
|
52
|
+
}
|
53
|
+
|
54
|
+
rb_ary_store( rbparams, count, key );
|
55
|
+
rb_ary_store( rbparams, count + 1, value );
|
56
|
+
|
57
|
+
count += 2;
|
58
|
+
return Qnil;
|
59
|
+
}
|