Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

RasterSourceF experimental implementation #185

Merged
merged 19 commits into from
Jul 18, 2019

Conversation

pomadchin
Copy link
Member

@pomadchin pomadchin commented Jun 4, 2019

Overview

This PR addresses #162 and #180

Demo

import cats.data.NonEmptyList
import cats.effect._
import cats.implicits._
import geotrellis.contrib.vlm.effect.MosaicRasterSource
import geotrellis.contrib.vlm.effect.geotiff._
import geotrellis.raster.{MultibandTile, Raster}
import geotrellis.vector.Extent

import scala.concurrent.ExecutionContext

val uri = "/tmp/aspect-tiled.tif"

object optcase {
  lazy val source: GeoTiffRasterSource[Option] = GeoTiffRasterSource[Option](uri)
  lazy val rasterSources = NonEmptyList(Option(GeoTiffRasterSource[Option](uri)), List(Option(GeoTiffRasterSource[Option](uri)), Option(GeoTiffRasterSource[Option](uri))))
  // lazy val msource = MosaicRasterSource[Option](rasterSources, source.crs)

  lazy val raster1: Option[Raster[MultibandTile]] = source.read(Extent(0, 0, 1, 1))
  lazy val raster2: Option[Raster[MultibandTile]] = source.read(Extent(630000.0, 215000.0, 639000.0, 219500.0))
  lazy val raster3: Option[Raster[MultibandTile]] = source.read()

  // lazy val mraster1: Option[Raster[MultibandTile]] = msource.read(Extent(0, 0, 1, 1))
  // lazy val mraster2: Option[Raster[MultibandTile]] = msource.read(Extent(630000.0, 215000.0, 639000.0, 219500.0))
  // lazy val mraster3: Option[Raster[MultibandTile]] = msource.read()

  def run = (raster1, raster2, raster3)

  // def mrun = (mraster1, mraster2, mraster3)

}

object iocase {
  implicit lazy val cs = IO.contextShift(ExecutionContext.global)

  // run in a main thread
  // implicit val cs = IO.contextShift(ExecutionContext.fromExecutor(new RasterSourceF.CurrentThreadExecutor))

  /*val i = 1000
  val n = 200
  val pool = Executors.newFixedThreadPool(n, new ThreadFactoryBuilder().setNameFormat("scala-sheets-%d").build())
  val ec = ExecutionContext.fromExecutor(pool)
  implicit val cs = IO.contextShift(ec)*/

  lazy val source: GeoTiffRasterSource[IO] = GeoTiffRasterSource[IO](uri)
  lazy val rasterSources = IO(NonEmptyList(GeoTiffRasterSource[IO](uri), List(GeoTiffRasterSource[IO](uri), GeoTiffRasterSource[IO](uri))))

  lazy val msource = MosaicRasterSource[IO](rasterSources, source.crs)

  lazy val raster1: IO[Raster[MultibandTile]] = source.read(Extent(0, 0, 1, 1))
  lazy val raster2: IO[Raster[MultibandTile]] = source.read(Extent(630000.0, 215000.0, 639000.0, 219500.0))
  lazy val raster3: IO[Raster[MultibandTile]] = source.read()

  lazy val mraster1: IO[Raster[MultibandTile]] = msource.read(Extent(0, 0, 1, 1))
  lazy val mraster2: IO[Raster[MultibandTile]] = msource.read(Extent(630000.0, 215000.0, 639000.0, 219500.0))
  lazy val mraster3: IO[Raster[MultibandTile]] = msource.read()

  println(s"${Thread.currentThread().getName}")

  lazy val result: Either[Throwable, List[Raster[MultibandTile]]] =
    List(
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3,
      raster2, raster3
    ).zipWithIndex
      .map { case (io, idx) => // add a thread printing
        IO.shift *> io.flatMap { v =>
          IO.shift *> IO {
            println(s"${idx}: ${Thread.currentThread().getName}")
            v
          }
        }
      }
      .parSequence
      .attempt
      .unsafeRunSync()

  lazy val mresult: Either[Throwable, List[Raster[MultibandTile]]] =
    List(
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3,
      mraster2, mraster3
    ).zipWithIndex
      .map { case (io, idx) => // add a thread printing
        IO.shift *> io.flatMap { v =>
          IO.shift *> IO {
            println(s"${idx}: ${Thread.currentThread().getName}")
            v
          }
        }
      }
      .parSequence
      .attempt
      .unsafeRunSync()

  def run = result
  def mrun = mresult
}

optcase.run
iocase.run
iocase.mrun

Checklist

Closes #162 #180

@pomadchin pomadchin requested a review from echeipesh June 10, 2019 21:08
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch from 32d69b6 to 6c93459 Compare June 10, 2019 21:14
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch from 20bbf15 to 294c418 Compare June 18, 2019 18:48
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch 3 times, most recently from 8757b92 to fca844b Compare June 18, 2019 19:35
build.sbt Show resolved Hide resolved
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch from fca844b to d0ce56f Compare June 18, 2019 19:58
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch 8 times, most recently from 74288ab to f8e5fef Compare June 23, 2019 01:42
@echeipesh echeipesh self-assigned this Jun 26, 2019
@echeipesh
Copy link
Collaborator

@pomadchin I'm not hip enough to understand the implications of using F[_]: Par constraint and how the magic works there, I'll need to educate myself there. However, this PR has a lot of good changes that need to happen and the RasterSourceF code looks and smells good.

I'd like to merge this optimistically after addressing single comment above and spend more time groking the async implementations when this is not blocking other work.

Copy link
Collaborator

@echeipesh echeipesh left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, the rebase is good and the effect/MosairRasterSource is good enough to test out more deeply

@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch 3 times, most recently from a6d5ece to 1b6e808 Compare July 9, 2019 20:32
@@ -33,7 +33,7 @@ class GeoTiffRasterSourceMultiThreadingSpec extends AsyncFunSpec with Matchers {

implicit val ec = ExecutionContext.global

val iterations = (0 to 100).toList
val iterations = (0 to 30).toList
Copy link
Member Author

@pomadchin pomadchin Jul 10, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Decreased the number of iterations to speed up an already slow tests set.

@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch from cee7425 to 44f1e6e Compare July 10, 2019 22:16
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch 2 times, most recently from 976ac80 to aff5895 Compare July 17, 2019 23:20
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch 4 times, most recently from 4da76bf to 5ccf470 Compare July 18, 2019 01:17
@pomadchin pomadchin force-pushed the feature/rs-effects-separate-par branch from 5ccf470 to 632e8de Compare July 18, 2019 16:38
@pomadchin
Copy link
Member Author

Merging!

@pomadchin pomadchin merged commit 19da0d8 into geotrellis:master Jul 18, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Add Effect Type for Raster Sources
2 participants