Skip to content

Commit 67d7cad

Browse files
authored
perf: optimize serialization tests for HTTP-backed services (#2525)
Skip redundant API calls in serialization round-trip tests for 61 HTTP service suites across 22 test files. These tests verify save/load/fit/ transform work correctly but don't need to compare output data (which requires live API calls that are slow and non-deterministic). - Fuzzing.scala: Transformer path uses transformSchema() instead of transform() when compareDataInSerializationTest=false. Estimator path verifies save/load/fit/transform succeed without comparing schemas (API-backed estimators produce non-deterministic field ordering). - Remove 14 dead assertDFEq overrides that were unreachable once the flag is false, along with unused imports and helper methods.
1 parent 4c04563 commit 67d7cad

22 files changed

Lines changed: 112 additions & 157 deletions

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/aifoundry/AIFoundryChatCompletionSuite.scala

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ import com.microsoft.azure.synapse.ml.core.test.fuzzing.{TestObject, Transformer
99
import com.microsoft.azure.synapse.ml.services.openai._
1010
import org.apache.spark.ml.util.MLReadable
1111
import org.apache.spark.sql.{DataFrame, Row}
12-
import org.scalactic.Equality
1312

1413
trait AIFoundryAPIKey {
1514
lazy val aiFoundryAPIKey: String = sys.env.getOrElse("AI_FOUNDRY_API_KEY", Secrets.AIFoundryApiKey)
@@ -18,6 +17,8 @@ trait AIFoundryAPIKey {
1817
}
1918

2019
class AIFoundryChatCompletionSuite extends TransformerFuzzing[AIFoundryChatCompletion] with AIFoundryAPIKey with Flaky {
20+
override val compareDataInSerializationTest: Boolean = false
21+
2122

2223
import spark.implicits._
2324

@@ -211,10 +212,6 @@ class AIFoundryChatCompletionSuite extends TransformerFuzzing[AIFoundryChatCompl
211212
assert(c.message.content.length > requiredLength)))
212213
}
213214

214-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
215-
super.assertDFEq(df1.drop("out"), df2.drop("out"))(eq)
216-
}
217-
218215
override def testObjects(): Seq[TestObject[AIFoundryChatCompletion]] =
219216
Seq(new TestObject(completion, goodDf))
220217

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/anomaly/AnamolyDetectionSuite.scala

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,8 @@ trait AnomalyDetectorSuiteBase extends TestBase with AnomalyKey {
6969
}
7070

7171
class DetectLastAnomalySuite extends TransformerFuzzing[DetectLastAnomaly] with AnomalyDetectorSuiteBase {
72+
override val compareDataInSerializationTest: Boolean = false
73+
7274

7375
lazy val ad: DetectLastAnomaly = new DetectLastAnomaly()
7476
.setSubscriptionKey(anomalyKey)
@@ -134,6 +136,8 @@ class DetectLastAnomalySuite extends TransformerFuzzing[DetectLastAnomaly] with
134136
}
135137

136138
class DetectAnomaliesSuite extends TransformerFuzzing[DetectAnomalies] with AnomalyDetectorSuiteBase {
139+
override val compareDataInSerializationTest: Boolean = false
140+
137141

138142
lazy val ad: DetectAnomalies = new DetectAnomalies()
139143
.setSubscriptionKey(anomalyKey)
@@ -172,6 +176,7 @@ class DetectAnomaliesSuite extends TransformerFuzzing[DetectAnomalies] with Anom
172176

173177
class SimpleDetectAnomaliesSuite extends TransformerFuzzing[SimpleDetectAnomalies]
174178
with AnomalyDetectorSuiteBase {
179+
override val compareDataInSerializationTest: Boolean = false
175180

176181
lazy val baseSeq = Seq(
177182
("1972-01-01T00:00:00Z", 826.0),

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/face/FaceSuite.scala

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,17 @@ package com.microsoft.azure.synapse.ml.services.face
66
import com.microsoft.azure.synapse.ml.services._
77
import com.microsoft.azure.synapse.ml.core.test.fuzzing.{TestObject, TransformerFuzzing}
88
import org.apache.spark.ml.util.MLReadable
9-
import org.apache.spark.sql.functions.{col, explode, lit}
9+
import org.apache.spark.sql.functions.{col, lit}
1010
import org.apache.spark.sql.{DataFrame, Row}
11-
import org.scalactic.Equality
1211

1312
import java.time.LocalDateTime
1413
import java.time.format.{DateTimeFormatterBuilder, DateTimeParseException, SignStyle}
1514
import java.time.temporal.ChronoField
1615
import scala.util.matching.Regex
1716

1817
class DetectFaceSuite extends TransformerFuzzing[DetectFace] with CognitiveKey {
18+
override val compareDataInSerializationTest: Boolean = false
19+
1920

2021
import spark.implicits._
2122

@@ -32,11 +33,6 @@ class DetectFaceSuite extends TransformerFuzzing[DetectFace] with CognitiveKey {
3233
.setReturnFaceLandmarks(true)
3334
.setReturnFaceAttributes(Seq("exposure"))
3435

35-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
36-
def prep(df: DataFrame) = df.select(explode(col("face"))).select("col.*").drop("faceId")
37-
super.assertDFEq(prep(df1), prep(df2))(eq)
38-
}
39-
4036
test("Basic Usage") {
4137
face.transform(df)
4238
val results = face.transform(df)
@@ -55,6 +51,8 @@ class DetectFaceSuite extends TransformerFuzzing[DetectFace] with CognitiveKey {
5551
}
5652

5753
class FindSimilarFaceSuite extends TransformerFuzzing[FindSimilarFace] with CognitiveKey {
54+
override val compareDataInSerializationTest: Boolean = false
55+
5856

5957
import spark.implicits._
6058

@@ -117,6 +115,8 @@ class FindSimilarFaceSuite extends TransformerFuzzing[FindSimilarFace] with Cogn
117115
}
118116

119117
class GroupFacesSuite extends TransformerFuzzing[GroupFaces] with CognitiveKey {
118+
override val compareDataInSerializationTest: Boolean = false
119+
120120

121121
import spark.implicits._
122122

@@ -178,6 +178,8 @@ class GroupFacesSuite extends TransformerFuzzing[GroupFaces] with CognitiveKey {
178178
}
179179

180180
class IdentifyFacesSuite extends TransformerFuzzing[IdentifyFaces] with CognitiveKey {
181+
override val compareDataInSerializationTest: Boolean = false
182+
181183

182184
import spark.implicits._
183185

@@ -328,6 +330,8 @@ class IdentifyFacesSuite extends TransformerFuzzing[IdentifyFaces] with Cognitiv
328330
}
329331

330332
class VerifyFacesSuite extends TransformerFuzzing[VerifyFaces] with CognitiveKey {
333+
override val compareDataInSerializationTest: Boolean = false
334+
331335

332336
import spark.implicits._
333337

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/form/FormOntologyLearnerSuite.scala

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,10 @@ import org.apache.spark.SparkException
88
import org.apache.spark.ml.util.MLReadable
99
import org.apache.spark.sql.DataFrame
1010
import org.apache.spark.sql.types.{ArrayType, DoubleType, StringType, StructType}
11-
import org.scalactic.Equality
1211

1312
class FormOntologyLearnerSuite extends EstimatorFuzzing[FormOntologyLearner] with FormRecognizerUtils {
13+
override val compareDataInSerializationTest: Boolean = false
14+
1415

1516
import spark.implicits._
1617

@@ -90,14 +91,6 @@ class FormOntologyLearnerSuite extends EstimatorFuzzing[FormOntologyLearner] wit
9091
assert(newDF.select("unified_ontology.*").collect().head.getAs[Double]("TotalTax") === 67.13)
9192
}
9293

93-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
94-
def prep(df: DataFrame) = {
95-
df.select("url", "unified_ontology.SubTotal")
96-
}
97-
98-
super.assertDFEq(prep(df1), prep(df2))(eq)
99-
}
100-
10194
override def testObjects(): Seq[TestObject[FormOntologyLearner]] =
10295
Seq(new TestObject(ontologyLearner, df))
10396

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/form/FormRecognizerSuite.scala

Lines changed: 11 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@ import org.apache.spark.ml.Transformer
2020
import org.apache.spark.ml.util.MLReadable
2121
import org.apache.spark.sql.DataFrame
2222
import org.apache.spark.sql.functions.col
23-
import org.scalactic.Equality
2423
import spray.json._
2524

2625
import java.net.URI
@@ -155,6 +154,8 @@ trait FormRecognizerUtils extends TestBase with CognitiveKey with Flaky with Ima
155154
}
156155

157156
class AnalyzeLayoutSuite extends TransformerFuzzing[AnalyzeLayout] with FormRecognizerUtils {
157+
override val compareDataInSerializationTest: Boolean = false
158+
158159

159160
lazy val analyzeLayout: AnalyzeLayout = new AnalyzeLayout()
160161
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
@@ -164,14 +165,6 @@ class AnalyzeLayoutSuite extends TransformerFuzzing[AnalyzeLayout] with FormReco
164165
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
165166
.setImageBytesCol("imageBytes").setOutputCol("layout").setConcurrency(5)
166167

167-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
168-
def prep(df: DataFrame) = {
169-
df.select("source", "layout.analyzeResult.readResults")
170-
}
171-
172-
super.assertDFEq(prep(df1), prep(df2))(eq)
173-
}
174-
175168
test("Basic Usage with URL") {
176169
val results = imageDf1.mlTransform(analyzeLayout,
177170
flattenReadResults("layout", "readlayout"),
@@ -219,6 +212,8 @@ class AnalyzeLayoutSuite extends TransformerFuzzing[AnalyzeLayout] with FormReco
219212
}
220213

221214
class AnalyzeReceiptsSuite extends TransformerFuzzing[AnalyzeReceipts] with FormRecognizerUtils {
215+
override val compareDataInSerializationTest: Boolean = false
216+
222217

223218
lazy val analyzeReceipts: AnalyzeReceipts = new AnalyzeReceipts()
224219
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
@@ -228,14 +223,6 @@ class AnalyzeReceiptsSuite extends TransformerFuzzing[AnalyzeReceipts] with Form
228223
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
229224
.setImageBytesCol("imageBytes").setOutputCol("receipts").setConcurrency(5)
230225

231-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
232-
def prep(df: DataFrame) = {
233-
df.select("source", "receipts.analyzeResult.readResults")
234-
}
235-
236-
super.assertDFEq(prep(df1), prep(df2))(eq)
237-
}
238-
239226
test("Basic Usage with URL") {
240227
val results = imageDf2.mlTransform(analyzeReceipts,
241228
flattenReadResults("receipts", "readReceipts"),
@@ -267,6 +254,8 @@ class AnalyzeReceiptsSuite extends TransformerFuzzing[AnalyzeReceipts] with Form
267254
}
268255

269256
class AnalyzeBusinessCardsSuite extends TransformerFuzzing[AnalyzeBusinessCards] with FormRecognizerUtils {
257+
override val compareDataInSerializationTest: Boolean = false
258+
270259

271260
lazy val analyzeBusinessCards: AnalyzeBusinessCards = new AnalyzeBusinessCards()
272261
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
@@ -276,14 +265,6 @@ class AnalyzeBusinessCardsSuite extends TransformerFuzzing[AnalyzeBusinessCards]
276265
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
277266
.setImageBytesCol("imageBytes").setOutputCol("businessCards").setConcurrency(5)
278267

279-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
280-
def prep(df: DataFrame) = {
281-
df.select("source", "businessCards.analyzeResult.readResults")
282-
}
283-
284-
super.assertDFEq(prep(df1), prep(df2))(eq)
285-
}
286-
287268
test("Basic Usage with URL") {
288269
val results = imageDf3.mlTransform(analyzeBusinessCards,
289270
flattenReadResults("businessCards", "readBusinessCards"),
@@ -317,6 +298,8 @@ class AnalyzeBusinessCardsSuite extends TransformerFuzzing[AnalyzeBusinessCards]
317298
}
318299

319300
class AnalyzeInvoicesSuite extends TransformerFuzzing[AnalyzeInvoices] with FormRecognizerUtils {
301+
override val compareDataInSerializationTest: Boolean = false
302+
320303

321304
lazy val analyzeInvoices: AnalyzeInvoices = new AnalyzeInvoices()
322305
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
@@ -326,14 +309,6 @@ class AnalyzeInvoicesSuite extends TransformerFuzzing[AnalyzeInvoices] with Form
326309
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
327310
.setImageBytesCol("imageBytes").setOutputCol("invoices").setConcurrency(5)
328311

329-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
330-
def prep(df: DataFrame) = {
331-
df.select("source", "invoices.analyzeResult.readResults")
332-
}
333-
334-
super.assertDFEq(prep(df1), prep(df2))(eq)
335-
}
336-
337312
test("Basic Usage with URL") {
338313
val results = imageDf4.mlTransform(analyzeInvoices,
339314
flattenReadResults("invoices", "readInvoices"),
@@ -377,6 +352,8 @@ class AnalyzeInvoicesSuite extends TransformerFuzzing[AnalyzeInvoices] with Form
377352
}
378353

379354
class AnalyzeIDDocumentsSuite extends TransformerFuzzing[AnalyzeIDDocuments] with FormRecognizerUtils {
355+
override val compareDataInSerializationTest: Boolean = false
356+
380357

381358
lazy val analyzeIDDocuments: AnalyzeIDDocuments = new AnalyzeIDDocuments()
382359
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
@@ -386,14 +363,6 @@ class AnalyzeIDDocumentsSuite extends TransformerFuzzing[AnalyzeIDDocuments] wit
386363
.setSubscriptionKey(cognitiveKey).setLocation("eastus")
387364
.setImageBytesCol("imageBytes").setOutputCol("ids").setConcurrency(5)
388365

389-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
390-
def prep(df: DataFrame) = {
391-
df.select("source", "ids.analyzeResult.readResults")
392-
}
393-
394-
super.assertDFEq(prep(df1), prep(df2))(eq)
395-
}
396-
397366
test("Basic Usage with URL") {
398367
val results = imageDf5.mlTransform(analyzeIDDocuments,
399368
flattenReadResults("ids", "readIds"),
@@ -439,6 +408,7 @@ trait CustomModelUtils extends TestBase with CognitiveKey {
439408

440409
class ListCustomModelsSuite extends TransformerFuzzing[ListCustomModels]
441410
with FormRecognizerUtils with CustomModelUtils {
411+
override val compareDataInSerializationTest: Boolean = false
442412

443413
lazy val listCustomModels: ListCustomModels = {
444414
new ListCustomModels()
@@ -449,14 +419,6 @@ class ListCustomModelsSuite extends TransformerFuzzing[ListCustomModels]
449419
.setConcurrency(5)
450420
}
451421

452-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
453-
def prep(df: DataFrame) = {
454-
df.select("models.summary.count")
455-
}
456-
457-
super.assertDFEq(prep(df1), prep(df2))(eq)
458-
}
459-
460422
ignore("List model list details") {
461423
val results = pathDf.mlTransform(listCustomModels,
462424
flattenModelList("models", "modelIds"))

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/form/FormRecognizerV3Suite.scala

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ import com.microsoft.azure.synapse.ml.core.test.fuzzing.{TestObject, Transformer
88
import org.apache.spark.ml.util.MLReadable
99
import org.apache.spark.sql.functions._
1010
import org.apache.spark.sql.{DataFrame, Row}
11-
import org.scalactic.Equality
1211

1312
import scala.collection.immutable.HashMap
1413

@@ -49,14 +48,7 @@ trait FormRecognizerV3Utils extends TestBase {
4948

5049
class AnalyzeDocumentSuite extends TransformerFuzzing[AnalyzeDocument] with FormRecognizerUtils
5150
with CustomModelUtils with FormRecognizerV3Utils {
52-
53-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
54-
def prep(df: DataFrame) = {
55-
df.select("source", "result.analyzeResult.content")
56-
}
57-
58-
super.assertDFEq(prep(df1), prep(df2))(eq)
59-
}
51+
override val compareDataInSerializationTest: Boolean = false
6052

6153
test("basic usage with tables") {
6254
val fromRow = AnalyzeDocumentResponse.makeFromRowConverter

cognitive/src/test/scala/com/microsoft/azure/synapse/ml/services/geospatial/AzureMapsSuite.scala

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@ import org.apache.http.entity.StringEntity
1515
import org.apache.spark.ml.util.MLReadable
1616
import org.apache.spark.sql.DataFrame
1717
import org.apache.spark.sql.functions.col
18-
import org.scalactic.Equality
1918

2019
import java.net.URI
2120

@@ -24,6 +23,8 @@ trait AzureMapsKey {
2423
}
2524

2625
class AzMapsSearchAddressSuite extends TransformerFuzzing[AddressGeocoder] with AzureMapsKey {
26+
override val compareDataInSerializationTest: Boolean = false
27+
2728

2829
import spark.implicits._
2930

@@ -71,10 +72,6 @@ class AzMapsSearchAddressSuite extends TransformerFuzzing[AddressGeocoder] with
7172
assert(flattenedResults.toSeq.head.get(1).toString.startsWith("47.6418"))
7273
}
7374

74-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
75-
super.assertDFEq(extractFields(df1), extractFields(df2))(eq)
76-
}
77-
7875
override def testObjects(): Seq[TestObject[AddressGeocoder]] =
7976
Seq(new TestObject[AddressGeocoder](
8077
batchGeocodeAddresses,
@@ -84,6 +81,8 @@ class AzMapsSearchAddressSuite extends TransformerFuzzing[AddressGeocoder] with
8481
}
8582

8683
class AzMapsSearchReverseAddressSuite extends TransformerFuzzing[ReverseAddressGeocoder] with AzureMapsKey {
84+
override val compareDataInSerializationTest: Boolean = false
85+
8786

8887
import spark.implicits._
8988

@@ -148,10 +147,6 @@ class AzMapsSearchReverseAddressSuite extends TransformerFuzzing[ReverseAddressG
148147

149148
}
150149

151-
override def assertDFEq(df1: DataFrame, df2: DataFrame)(implicit eq: Equality[DataFrame]): Unit = {
152-
super.assertDFEq(extractFields(df1), extractFields(df2))(eq)
153-
}
154-
155150
override def testObjects(): Seq[TestObject[ReverseAddressGeocoder]] =
156151
Seq(new TestObject[ReverseAddressGeocoder](
157152
batchReverseGeocode,

0 commit comments

Comments
 (0)