Before I actually run into the development of the xsd helper, I would like to express some few points regarding how this helper will actually work:

1.The input to the xsd helper will be an xml file and an xsd file against which the ml is supposed to be validated

2. the Output will be the a message indicating the validation status.

So, here goes the actual helper i.e Xsd_Helper.rb

module XsdHelper

I require the fileutils and tempfile libs for file object manipulation

  require ‘fileutils’

  require ‘tempfile’

I define the FILE_HOME  and the XML_STARTLET HOME.In the file home, I create 2 files finalxsd.xsd and finalxml.xml which we are going to see later.In the xmlstartlet home I keep the xmlstartlet library.Here I have kept the library in the public folder of our app.

    FILE_HOME = “#{RAILS_ROOT}/public/temp”

    XMLSTARTLET_HOME =”#{RAILS_ROOT}/public/xmlstartlet”

Now , we write the actual method which validates the xml against the xsd. We pass 2 parameters to the method i.e the xsdfile and the xmlfile

   def validate_xml_to_xsd(xsdfile,xmlfile)

@temp_xsd =validate(xsdfile)

            @temp_xml =validate(xmlfile)

We have to validate the xmlfiles and xsdfiles type in this case since in rails files below the size of 10kb are passed as a STRINGIO object and files above 10kb are passed as the TempFile Object . So, This validate method converts the STRINGIO object into the TEMPFILE object .

   

     finalxsd = File.new(FILE_HOME+”/finalxsd.xsd”,”w”)

     finalxml = File.new(FILE_HOME+”/finalxml.xml”,”w”)

Here,I create 2 new files in the FILE_HOME named finalxsd.xsd and finalxml.xsd.the purpose of these 2 files is, since, xmlstartlet library takes does not support the tempfile object

  FileUtils.copy(”#{@temp_xsd.path}”,”#{finalxsd.path}”)

  FileUtils.copy(”#{@temp_xml.path}”,”#{finalxml.path}”)

Here I copy the two file content from the temporary file to the respective xml and xsd file command_line=”#{XMLSTARTLET_HOME}/xml val -s “+ “#{finalxsd.path}” +’ ‘+”#{finalxml.path}”

  result_string = %x[#{command_line}] 

Then , I pass the two files to the xmlstratlet commandline utility for the actaual validation of the xml file

 assess_validation_result(result_string)

The access validation result takes the result string as the input and customizes the output which is returned to our rails controller as a Boolean output

   end

 

  private

 

  def assess_validation_result(result_string)

                        if (result_string=~/.+xml - invalid/).nil? then

                  true

                        else

                    raise result_string 

                        end

  end

       

def validate(file)

  @file = file

  # @file should contain file uploaded by HTTP

  # it is either StringIO object (if file was smaller than 10Kb)

  # or Tempfile (otherwise)

  if not (@file.kind_of? StringIO or @file.kind_of? Tempfile)

       return

  end

   if @file.kind_of? StringIO

    # Yes, if @file is StringIO, create new Tempfile and copy everything to it

     @real_file = Tempfile.new(”tempofile”)

    while not @file.eof?

      @real_file.write @file.read

    end

  else

   # Most uploads will be Tempfiles

    @real_file = @file

  end

   return @real_file

end

end

So,finally in the controller action, You can call the validate_xml_to_xsd(xsdfile,xmlfile) as ashoen below:

def input
    if request.post? && !params.nil?    
        @validate_output = validate_xml_to_xsd(params[’fileinfo’][’xsd_file’],params[’fileinfo’][’xml_file’])

if(@validate_output == true)

             flash[:notice] =”Your xml has been successfully validated”

end

render :action =>  ‘output’
      else
        render :action => ‘input’

       flash[:notice] = “Failed to validate the xml file”
          end
     end
end

 

Share and Enjoy: These icons link to social bookmarking sites where readers can share and discover new web pages.
  • Digg
  • del.icio.us
  • blogmarks
  • Book.mark.hu
  • co.mments
  • Technorati
  • YahooMyWeb
  • IndianPad
  • DZone