Akka Http client type mismatch - scala

Can anyone tell me why I'm getting the following error?:
[error] HttpClient.scala:117: type mismatch;
[error] found : akka.stream.scaladsl.Sink[(akka.http.scaladsl.model.StatusCode, String),scala.concurrent.Future[(akka.http.scaladsl.model.StatusCode, String)]]
[error] required: akka.stream.Graph[akka.stream.SinkShape[(akka.http.scaladsl.model.StatusCode, String)],scala.concurrent.Future[akka.http.scaladsl.model.StatusCode]]
[error] source.via(flow).runWith(Sink.head)
[error] ^
Here's the code:
implicit def map2entity: ToEntityMarshaller[Map[String, Any]] = mapMarshaller(MediaTypes.`application/json`)
def mapMarshaller(mediaType: MediaType.WithFixedCharset): ToEntityMarshaller[Map[String, Any]] =
Marshaller.withFixedContentType(mediaType) { m => HttpEntity(mediaType, JSONObject(m).toString()) }
def post(path: String, entity: Map[String, Any]): Future[StatusCode] = {
val uri = Uri(getResourceUri(path))
logger.info(s"httpPost: $uri")
Marshal(entity).to[RequestEntity] flatMap { e =>
val source = Source.single(HttpRequest(
uri = uri.path.toString,
method = HttpMethods.POST,
entity = e))
val flow = getConnection(uri.scheme)(uri.authority.host.address)
.mapAsync(10) { r =>
//(r.status -> Marshal(r.entity).to[String])
Unmarshal(r.entity).to[String].flatMap(s => Future(r.status -> s))
}
source.via(flow).runWith(Sink.head)
}
}

The materialized value of your sink (Future[(StatusCode, String)]) is different from the return type you declared in the function (Future[StatusCode]).
If you post function only needs to return the status code, you can change this call
.flatMap(s => Future(r.status -> s))
To this
.map(_ => r.status)

Related

cannot be applied to (play.api.mvc.AnyContent)

when i try to convert my content of request body to json this happens..
code:
def addItem() = Action { implicit request =>
val content:AnyContent = request.body
val res = Json.parse(content)
Ok("done")
}
sbt compile msg:
**overloaded method parse with alternatives:
[error] (input: Array[Byte])play.api.libs.json.JsValue <and>
[error] (input: java.io.InputStream)play.api.libs.json.JsValue <and>
[error] (input: String)play.api.libs.json.JsValue
[error] cannot be applied to (play.api.mvc.AnyContent)
[error] val res = Json.parse(content)**
i want to know why i can't convert my content as json ?
AnyContent provides a helper method asJson:
ef addItem() = Action { implicit request =>
val content: AnyContent = request.body
val res: Option[JsValue] = content.asJson
Ok("done")
}
Or, you can use Play's body parser directly:
def addItem() = Action(parse.json) { implicit request: Request[JsValue] =>
val content: JsValue = request.body
// ...
Ok("done")
}
It will give a HTTP 400 automatically if content is not JSON.
See https://www.playframework.com/documentation/2.8.x/ScalaBodyParsers

Type mismatch in recursive function using Bitbucket API and Playframework

I created a generic function to get from Bitbucket-API (It gives you the data in pages if there is to much data and the next page URL is under "next" in the response).
def getAggregatedDataWithNext[T](url: String)(implicit reader: Reads[T]): Future[Seq[T]]= {
val featureResponse = ws.url(url).withAuth(AuthUserName, AuthPassword, WSAuthScheme.BASIC).addQueryStringParameters("pagelen" -> "100").get()
featureResponse.map(response => {
val resJson = response.json
val tSequence = (resJson \ "values").as[Seq[T]]
(resJson \ "next").asOpt[String] match {
case None => tSequence
case Some(nextUrl) => getAggregatedDataWithNext(nextUrl).flatMap(tSequence ++ _)
}
})
}
I get an error:
type mismatch;
found : Seq[T]
required: scala.concurrent.Future[?]
And IntelliJ gives me this:

In Scala,Set convert to Map error.Cannot prove that (String, Class[?0]) forSome { type ?0 } <:< (T, U)

This code is working properly
def init = {
var jobPackageClassSet:Set[Class[_]] = ClassUtil.getClassSetFromPackge("com.test.job");
val jobAnnotion = classOf[JobAnnotation];
val a = jobPackageClassSet.asScala.filter { cls =>
cls.isAnnotationPresent(jobAnnotion)
}.map(cls => cls.getAnnotation(jobAnnotion).jobName -> cls.getName).toMap
}
But when I change the code (cls.getAnnotation(jobAnnotion).jobName -> cls) as below,it causes error
def init = {
var jobPackageClassSet = ClassUtil.getClassSetFromPackge("com.test.job");
val jobAnnotion = classOf[JobAnnotation];
val a = jobPackageClassSet.asScala.filter { cls =>
cls.isAnnotationPresent(jobAnnotion)
}.map(cls => cls.getAnnotation(jobAnnotion).jobName -> cls).toMap
}
Error:
Cannot prove that (String, Class[?0]) forSome { type ?0 } (T, U). not
enough arguments for method toMap
From this question:Cannot prove that Unit <:< (T, U) change my code to this, is still the error.
def init = {
var jobPackageClassSet = ClassUtil.getClassSetFromPackge("com.test.job");
val jobAnnotion = classOf[JobAnnotation];
val a = jobPackageClassSet.asScala.filter { cls =>
cls.isAnnotationPresent(jobAnnotion)
}.map(cls => cls.getAnnotation(jobAnnotion).jobName -> cls).collect{case t#(k:String,v:Class[_]=>t)}.toMap
}
Has anyone got this earlier?
The problem is that toMap can only be called on a sequence (or set) of pairs, but for some reason you have a sequence of existential types, each of which is a pair. You want (String, Class[?0] forSome { type ?0 }) rather than (String, Class[?0]) forSome { type ?0 }, though it isn't obvious to me why your current code gets the wrong type (what is the return type of ClassUtil.getClassSetFromPackge)?
I expect .map(cls => cls.getAnnotation(jobAnnotion).jobName -> (cls: Class[_])) or .map { case cls: Class[_] => cls.getAnnotation(jobAnnotion).jobName -> cls } should fix the problem.
I know this is old issue, but I post for whoever arrives here nowadays :)
I had same error today with other types:
val seq: Seq[(String, com.company.complicatedUnionClass)] = //.....
val mapped = seq.toMap
Cannot prove that (String, _ >: com.company.complicatedUnionClass) forSome { type _$8 >: com.company.complicatedUnionClass } <:< (T, U)
adding explicitly the [T,U] parameter in toMap solved the compilation error
val seq: Seq[(String, com.company.complicatedUnionClass)] = //.....
val mapped = seq.toMap[String, com.company.complicatedUnionClass]

Weird type mismatch error in Scala

Already asked at scala-user, didn't get an answer.
I expect the below to compile:
trait Elems {
trait Dummy
abstract class Elem[A] extends Serializable with Dummy
class BaseElem[A] extends Elem[A]
implicit val BooleanElement: Elem[Boolean] = new BaseElem[Boolean]
implicit val ByteElement: Elem[Byte] = new BaseElem[Byte]
implicit val ShortElement: Elem[Short] = new BaseElem[Short]
implicit val IntElement: Elem[Int] = new BaseElem[Int]
implicit val LongElement: Elem[Long] = new BaseElem[Long]
implicit val FloatElement: Elem[Float] = new BaseElem[Float]
implicit val DoubleElement: Elem[Double] = new BaseElem[Double]
implicit val UnitElement: Elem[Unit] = new BaseElem[Unit]
implicit val StringElement: Elem[String] = new BaseElem[String]
implicit val CharElement: Elem[Char] = new BaseElem[Char]
}
trait GoodMatch { self: Elems =>
private def boxed_class(e: Elem[_]): Class[_] = e match {
case BooleanElement => classOf[java.lang.Boolean]
case ByteElement => classOf[java.lang.Byte]
case ShortElement => classOf[java.lang.Short]
case IntElement => classOf[java.lang.Integer]
case LongElement => classOf[java.lang.Long]
case FloatElement => classOf[java.lang.Float]
case DoubleElement => classOf[java.lang.Double]
case CharElement => classOf[java.lang.Character]
case _ => ???
}
}
abstract class BadMatch[+A <: Elems](scalan: A) {
import scalan._
protected def toLuaValue(x: Any, eX: Elem[_]): String = eX match {
case UnitElement => ""
case _ => ???
}
// should check type before conversion?
protected def fromLuaValue[B](lv: Any, eA: Elem[B]): B = (eA match {
case UnitElement => ()
}).asInstanceOf[B]
}
And GoodMatch does, but BadMatch fails (in Scala 2.11.8):
[error] /tmp/rendererqu0xjasKpX/src/main/scala/test.scala:48: type mismatch;
[error] found : BadMatch.this.scalan.Elem[Unit]
[error] required: BadMatch.this.scalan.Elem[_$3] where type _$3
[error] case UnitElement => ""
[error] ^
[error] /tmp/rendererqu0xjasKpX/src/main/scala/test.scala:63: type mismatch;
[error] found : BadMatch.this.scalan.Elem[Unit]
[error] required: BadMatch.this.scalan.Elem[B]
[error] case UnitElement => ()
[error] ^
Removing with Dummy makes BadMatch compile as well.
Is this a Scala bug? If so, is it a known one?
Yes, it's a Scala compiler bug: https://issues.scala-lang.org/browse/SI-9779.

Slick select using value object (extending AnyVal)

I am using Slick 2.1.0 with Scala 2.10.
I have a value object (EMail) that I map to a VARCHAR column.
object EMail {
import java.util.regex.Pattern
val emailRegex = Pattern.compile("^[A-Z0-9._%+-]+#[A-Z0-9.-]+\\.[A-Z]{2,6}$", Pattern.CASE_INSENSITIVE)
val empty = EMail("x#y.com")
}
case class EMail(value: String) extends AnyVal with MappedTo[String] {
def isValid: Boolean = EMail.emailRegex.matcher(value).find
def validate: EMail = {
assert(isValid)
EMail(value.trim.toLowerCase)
}
override def toString = validate.value
}
The Column definition is:
def email = column[Option[EMail]]("email_address")
This is my attempt at writing a finder:
def findByEmail(email: Option[EMail]): Option[User] =
database.withSession { implicit session: Session =>
queryAll.filter(e => e.email.isDefined && e.email === email).firstOption
}
This is the error message I get:
[error] Users.scala:52: ambiguous implicit values:
[error] both value BooleanCanBeQueryCondition in object CanBeQueryCondition of type => scala.slick.lifted.CanBeQueryCondition[Boolean]
[error] and value BooleanOptionColumnCanBeQueryCondition in object CanBeQueryCondition of type => scala.slick.lifted.CanBeQueryCondition[scala.slick.lifted.Column[Option[Boolean]]]
[error] match expected type scala.slick.lifted.CanBeQueryCondition[Nothing]
[error] queryAll.filter(_.email === email.map(_.value)).firstOption
[error] ^
You don't have to pass an Option[EMail] to your method, you could simply make:
def findByEmail(email: EMail): Option[User] = {
database.withSession { implicit session =>
queryAll.filter(_.email === email).firstOption
}
}
If you really need an Option[EMail]] as the input parameter, you should try the following:
def findByEmail(emailOpt: Option[EMail]): Option[User] = {
emailOpt.flatMap { email =>
database.withSession { implicit session =>
queryAll.filter(_.email === email).firstOption
}
}
}