/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.apache.spark.sql

import org.apache.spark.SparkFunSuite
import org.apache.spark.sql.catalyst.util.{fileToString, stringToFile, CollationFactory}

// scalastyle:off line.size.limit
/**
 * Guard against breaking changes in ICU locale names and codes supported by Collator class and provider by CollationFactory.
 * Map is in form of rows of pairs (locale name, locale id); locale name consists of three parts:
 * - 2-letter lowercase language code
 * - 4-letter script code (optional)
 * - 3-letter uppercase country code
 *
 * To re-generate collations map golden file, run:
 * {{{
 *   SPARK_GENERATE_GOLDEN_FILES=1 build/sbt "sql/testOnly org.apache.spark.sql.ICUCollationsMapSuite"
 * }}}
 */
// scalastyle:on line.size.limit
class ICUCollationsMapSuite extends SparkFunSuite {

  private val collationsMapFile = {
    getWorkspaceFilePath("sql", "core", "src", "test", "resources",
      "collations", "ICU-collations-map.md").toFile
  }

  if (regenerateGoldenFiles) {
    val map = CollationFactory.getICULocaleNames
    val mapOutput = map.zipWithIndex.map {
      case (localeName, idx) => s"| $idx | $localeName |" }.mkString("\n")
    val goldenOutput = {
      s"<!-- Automatically generated by ${getClass.getSimpleName} -->\n" +
      "## ICU locale ids to name map\n" +
      "| Locale id | Locale name |\n" +
      "| --------- | ----------- |\n" +
      mapOutput + "\n"
    }
    val parent = collationsMapFile.getParentFile
    if (!parent.exists()) {
      assert(parent.mkdirs(), "Could not create directory: " + parent)
    }
    stringToFile(collationsMapFile, goldenOutput)
  }

  test("ICU locales map breaking change") {
    val goldenLines = fileToString(collationsMapFile).split('\n')
    val goldenRelevantLines = goldenLines.slice(4, goldenLines.length) // skip header
    val input = goldenRelevantLines.map(
      s => (s.split('|')(2).strip(), s.split('|')(1).strip().toInt))
    assert(input sameElements CollationFactory.getICULocaleNames.zipWithIndex)
  }
}
