Why nested class call like this "val statusData:StatusData?=StatusData()"? - java

Why nested class call in this way val statusData:StatusData?=StatusData().
class NestedModel{
var id: String? = null
val statusData:StatusData?=StatusData() // Like this
class StatusData {
var internal_status: String? = null
var ot_code: String? = null
}
}

Your question is not understandable. But i thing your question is this. Why we can not call StatusData() from nestedModel object. For this we use "inner class" key word.
Example:
fun main() {
val nestedModel = NestedModel()
val statusData = nestedModel.StatusData()
}
class NestedModel {
var id: String? = null
inner class StatusData {
var internal_status: String? = null
var ot_code: String? = null
}
}

Related

Scala udf UnsupportedOperationException

I have a dataframe a2 written in scala :
val a3 = a2.select(printme.apply(col(“PlayerReference”)))
the column PlayerReference contains a string.
that calls an udf function :
val printme = udf({
st: String =>
val x = new JustPrint(st)
x.printMe();
})
this udf function calls a java class :
public class JustPrint {
private String ss = null;
public JustPrint(String ss) {
this.ss = ss;
}
public void printMe() {
System.out.println("Value : " + this.ss);
}
}
but i have this error for the udf :
java.lang.UnsupportedOperationException: Schema for type Unit is not supported
The goal of this exercise is to validate the chain of calls.
What should I do to solve this problem ?
The reason you're getting this error is that your UDF doesn't return anything, which, in terms of spark is called Unit.
What you should do depends on what you actually want, but, assuming you just want to track values coming through your UDF you should either change printMe so it returns String, or the UDF.
Like this:
public String printMe() {
System.out.println("Value : " + this.ss);
return this.ss;
}
or like this:
val printme = udf({
st: String =>
val x = new JustPrint(st)
x.printMe();
x
})

Extract specific token out of ANTLR Parse Tree

i'm trying to extract data from the ANTLR parse tree, but not fully grasping how this should be done correctly
Let's say i have the following two SQL queries:
// language=SQL
val sql3 = """
CREATE TABLE session(
id uuid not null
constraint account_pk
primary key,
created timestamp default now() not null
)
""".trimIndent()
// language=SQL
val sql4 = """
CREATE TABLE IF NOT EXISTS blah(
id uuid not null
constraint account_pk
primary key,
created timestamp default now() not null
)
""".trimIndent()
Now i parse both of them:
val visitor = Visitor()
listOf(sql3, sql4).forEach { sql ->
val lexer = SQLLexer(CharStreams.fromString(sql))
val parser = SQLParser(CommonTokenStream(lexer))
visitor.visit(parser.sql())
println(visitor.tableName)
}
In my visitor if i visit the tableCreateStatement, i get the parse tree, but obviously just grabbing child1 will work for sql3, but not for sql4 since child1 in sql4 is IF NOT EXISTS
class Visitor : SQLParserBaseVisitor<Unit>() {
var tableName = ""
override fun visitCreate_table_statement(ctx: SQLParser.Create_table_statementContext?) {
tableName = ctx?.getChild(1)?.text ?: ""
super.visitCreate_table_statement(ctx)
}
}
Is there a way to find a specific token in the parse tree?
I'm assuming the payload has something to do with it, but since it's of type Any, i'm not sure what to check it against
override fun visitCreate_table_statement(ctx: SQLParser.Create_table_statementContext?) {
ctx?.children?.forEach {
if (it.payload.javaClass == SQLParser::Schema_qualified_nameContext) {
tableName = it.text
}
}
super.visitCreate_table_statement(ctx)
}
EDIT: the .g4 files are from
https://github.com/pgcodekeeper/pgcodekeeper/tree/master/apgdiff/antlr-src
this seems to work
override fun visitCreate_table_statement(ctx: SQLParser.Create_table_statementContext?) {
ctx?.children?.forEach {
if (it.payload.javaClass == Schema_qualified_nameContext::class.java) {
tableName = it.text
}
}
super.visitCreate_table_statement(ctx)
}
For branching trees
fun walkLeaves(
childTree: ParseTree = internalTree,
leave: (childTree: ParseTree) -> Unit) {
if (childTree.childCount == 0) {
if (!childTree.text?.trim().isNullOrBlank()) {
leave(childTree)
}
} else {
for (i in 0 until childTree.childCount) {
walkLeaves(childTree = childTree.getChild(i), leave = leave)
}
}
}
fun extractSQL(
childTree: ParseTree,
tokens: MutableList<String> = mutableListOf()
): String {
walkLeaves(childTree = childTree) { leave ->
tokens.add(leave.text)
}
...
}

Junit expected value exception

I am writing a test to test my repository. I noticed that the return expected value matches the actual value except that the actual value is wrapped within "<>".
I do not know why this is happening.
#ExperimentalCoroutinesApi
#RunWith(AndroidJUnit4::class)
#Config(sdk = [Build.VERSION_CODES.O_MR1])
class MovieRepositoryTest{
#get:Rule
var instantExecutorRule = InstantTaskExecutorRule()
private val movie1 = MovieEntity("Title1", "https://movie1.jpg", 3, "Movie1Overview", "Jan 2021")
private val movie2 = MovieEntity("Title2", "https://movie2.jpg", 3, "Movie2Overview", "Jan 2022")
private val movie3 = MovieEntity("Title3", "https://movie3.jpg", 3, "Movie2Overview", "Jan 2023")
private val remoteTasks = mutableListOf(movie3).sortedBy { it.id }
private val localTasks = mutableListOf(movie1, movie2).sortedBy { it.id }
private lateinit var tasksRemoteDataSource: FakeDataSource<MovieEntity>
private lateinit var tasksLocalDataSource: FakeDataSource<MovieEntity>
private lateinit var moviesRepository: MoviesRepoInterface
#Before
fun createRepository() {
tasksRemoteDataSource = FakeDataSource(remoteTasks.toMutableList())
tasksLocalDataSource = FakeDataSource(localTasks.toMutableList())
moviesRepository = MovieRepository(tasksRemoteDataSource, tasksLocalDataSource)
}
#Test
fun getRemoteMovies_RequestAllMovie()= runBlockingTest{
val movies = moviesRepository.getMovies(false, ApplicationProvider.getApplicationContext())
assertEquals(movies.getOrAwaitValue(), IsEqual<List<MovieEntity>>(localTasks))
}
}
Error
java.lang.AssertionError:
Expected :[com.darotapp.cornflix.data.local.database.MovieEntity#3843fe46, com.darotapp.cornflix.data.local.database.MovieEntity#1b40b010]
Actual :<[com.darotapp.cornflix.data.local.database.MovieEntity#3843fe46, com.darotapp.cornflix.data.local.database.MovieEntity#1b40b010]>
The data class for the table is below
Table
#Entity
data class MovieEntity(
var title: String?,
var movieImage:String?,
var rating:Int?,
var overView:String?,
var releaseDate:String?
): Serializable {
operator fun component1(): String? = title
operator fun component2(): String? = movieImage
operator fun component3(): Int? = rating
operator fun component4(): String? = overView
operator fun component5(): String? = releaseDate
#PrimaryKey()
var id: Int = 0
var favourite:Boolean = false
var movieId:String? = ""
}
I finally figured it out. The problem was using IsEqual. I was able to correct this with the code below.
val movies = moviesRepository.getMovies(false, ApplicationProvider.getApplicationContext())
assertEquals(movies?.value, Matchers.equalTo(localTasks))

Is possible to access $loader variable I see in the debug window?

As you can see in this screenshot while I'm in debug mode i can see a $loader variable that has the "() -> com.belandsoft.orariGTT.Model.RestRequestResponse, kotlin.Boolean>" content. It's possible to access these value at runtime in any way? The reflection can be helpfull in any way?
Sample code:
val mCollection: kotlin.collections.HashMap<Int, () -> Unit> = HashMap()
fun <T> myAddFunction(loader: () -> T) {
val elementCode = loader?.hashCode()
if (elementCode != null) {
mCollection[elementCode] = loader
}
}
fun myPrintFunction(): String {
val stringBuilder = StringBuilder()
var index = 0
for (i in mCollection.iterator()) {
stringBuilder.append("$index:[${i.value}] ")
index++
}
stringBuilder.toString()
}
This sadly produces a string like:
"053523:[()->kotlin.Unit], 453455:[()->kotlin.Unit]"
but I want to have:
"053523:[()->com.belandsoft.orariGTTView.MainFragment$startPtArrivalSearch$2$18839], 453455:[()->com.belandsoft.orariGTTView.MainFragment$startPtArrivalSearch$2$18845]"
Thanks.

Riak Java Client annotation not recognized in Scala case class?

I am using case classes to define different "models" of data in our app. Reason is to enable easy use of Jerkson (Scala interface to Jackson). To convert my User to a domain object in Riak I have used the #RiakKey annotation on my guid. I have the following:
case class User(
#RiakKey val guid: String,
#RiakIndex(name = "email") val email: String,
val salt: String,
val passwordHash: String,
val emailHash: String,
val firstName: String,
val lastName: String,
val suspended: Boolean=false,
val created: Timestamp=now
)
When I go to perform a domain conversion on the case class, the #RiakKey isn't recognized. It throws an NoKeySpecifedException. Here's my converter:
class UserConverter(val bucket: String) extends Converter[User] {
def fromDomain(domainObject: User, vclock: VClock) = {
val key = getKey(domainObject)
if(key == null) throw new NoKeySpecifedException(domainObject)
val kryo = new Kryo()
kryo.register(classOf[User])
val ob = new ObjectBuffer(kryo)
val value = ob.writeObject(domainObject)
RiakObjectBuilder.newBuilder(bucket, key)
.withValue(value)
.withVClock(vclock)
.withContentType(Constants.CTYPE_OCTET_STREAM)
.build()
}
}
Is this an issue in Scala with Java annotations? Is there a workaround?
Update
Here's where the User object is created and stored, and where the converter is referenced:
1)
val user = parse[User](body) // jerkson parse, body is a string of JSON
User.store(user)
2)
object User {
val bucketName = "accounts-users"
val bucket = DB.client.createBucket(bucketName).execute()
def fetch(id: String) = bucket.fetch(id).execute().getValueAsString()
def store(o: User) = bucket.store( o ).withConverter(new UserConverter(bucketName)).execute()
}
Strack Trace
com.basho.riak.client.convert.NoKeySpecifedException
at com.basho.riak.client.bucket.DefaultBucket.store(DefaultBucket.java:455)
at com.threetierlogic.AccountService.models.User$.store(User.scala:58)
at com.threetierlogic.AccountService.controllers.Users$$anonfun$routes$3.apply(Users.scala:54)
at com.threetierlogic.AccountService.controllers.Users$$anonfun$routes$3.apply(Users.scala:51)
(I apologize for the long conversation before this answer)
After learning a bit more about scala I discovered that with a case class you have to do it a little differently.
http://piotrbuda.eu/2012/10/scala-case-classes-and-annotations-part-1.html
If you do:
#(RiakKey#field) guid: String
it works.
I wrote a small test program in scala and was able to extract the annotated key using the static getKey() method used in the DefaultBucket that was returning null and causing the exception to be thrown.
import com.basho.riak.client.convert.KeyUtil.getKey;
object Main {
def main(args: Array[String]): Unit = {
val u = User("my_key")
val k = getKey(u)
System.out.println(k);
}
}
User.scala
/* scala 2.9.1 would be scala.annotation.target.field */
import scala.annotation.meta.field
import com.basho.riak.client.convert.RiakKey;
case class User (#(RiakKey#field) guid: String)
Output:
my_key
(And, if you change the annotation back to the way you had it, it returns null as expected)
Here's my proposed workaround for the problem. Instead of relying on annotations, I am just going to use the DefaultBucket.store method and manually designate a key.
My User companion object:
object User {
val bucketName = "accounts-users"
val bucket = DB.client.createBucket(bucketName).execute()
def store(key: String, o: User) = bucket.store(key, o).withConverter(new UserConverter(bucketName)).execute()
}
And using it:
val user = parse[User](body)
User.store(user.guid, user)

Categories

Resources